From 38064be702a9418864a7675bb44f3d213053e032 Mon Sep 17 00:00:00 2001 From: Stypox Date: Mon, 28 Jul 2025 23:54:47 +0200 Subject: [PATCH 1/7] Add more specific error messages and deduplicate their handling --- app/build.gradle | 2 +- .../org/schabi/newpipe/RouterActivity.java | 34 +++---------------- .../org/schabi/newpipe/error/ErrorInfo.kt | 34 +++++++++++++++++-- .../schabi/newpipe/error/ErrorPanelHelper.kt | 31 +---------------- .../org/schabi/newpipe/error/ErrorUtil.kt | 2 +- .../org/schabi/newpipe/error/UserAction.java | 3 +- .../util/text/InternalUrlsHandler.java | 23 +++++-------- app/src/main/res/values/strings.xml | 2 ++ 8 files changed, 52 insertions(+), 79 deletions(-) diff --git a/app/build.gradle b/app/build.gradle index dbffc2bf6c3..7f4166a5754 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -214,7 +214,7 @@ dependencies { // the corresponding commit hash, since JitPack sometimes deletes artifacts. // If there’s already a git hash, just add more of it to the end (or remove a letter) // to cause jitpack to regenerate the artifact. - implementation 'com.github.TeamNewPipe:NewPipeExtractor:v0.24.8' + implementation 'com.github.Stypox:NewPipeExtractor:b8bd4cda8cca00a14940933e3d3635d5aafec222' implementation 'com.github.TeamNewPipe:NoNonsense-FilePicker:5.0.0' /** Checkstyle **/ diff --git a/app/src/main/java/org/schabi/newpipe/RouterActivity.java b/app/src/main/java/org/schabi/newpipe/RouterActivity.java index 3294cae0b03..dac2d29a126 100644 --- a/app/src/main/java/org/schabi/newpipe/RouterActivity.java +++ b/app/src/main/java/org/schabi/newpipe/RouterActivity.java @@ -58,20 +58,13 @@ import org.schabi.newpipe.extractor.StreamingService; import org.schabi.newpipe.extractor.StreamingService.LinkType; import org.schabi.newpipe.extractor.channel.ChannelInfo; -import org.schabi.newpipe.extractor.exceptions.AgeRestrictedContentException; import org.schabi.newpipe.extractor.exceptions.ContentNotAvailableException; import org.schabi.newpipe.extractor.exceptions.ContentNotSupportedException; import org.schabi.newpipe.extractor.exceptions.ExtractionException; -import org.schabi.newpipe.extractor.exceptions.GeographicRestrictionException; -import org.schabi.newpipe.extractor.exceptions.PaidContentException; -import org.schabi.newpipe.extractor.exceptions.PrivateContentException; import org.schabi.newpipe.extractor.exceptions.ReCaptchaException; -import org.schabi.newpipe.extractor.exceptions.SoundCloudGoPlusContentException; -import org.schabi.newpipe.extractor.exceptions.YoutubeMusicPremiumContentException; import org.schabi.newpipe.extractor.linkhandler.ListLinkHandler; import org.schabi.newpipe.extractor.playlist.PlaylistInfo; import org.schabi.newpipe.extractor.stream.StreamInfo; -import org.schabi.newpipe.ktx.ExceptionUtils; import org.schabi.newpipe.local.dialog.PlaylistDialog; import org.schabi.newpipe.player.PlayerType; import org.schabi.newpipe.player.helper.PlayerHelper; @@ -279,28 +272,11 @@ private static void handleError(final Context context, final ErrorInfo errorInfo final Intent intent = new Intent(context, ReCaptchaActivity.class); intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); context.startActivity(intent); - } else if (errorInfo.getThrowable() != null - && ExceptionUtils.isNetworkRelated(errorInfo.getThrowable())) { - Toast.makeText(context, R.string.network_error, Toast.LENGTH_LONG).show(); - } else if (errorInfo.getThrowable() instanceof AgeRestrictedContentException) { - Toast.makeText(context, R.string.restricted_video_no_stream, - Toast.LENGTH_LONG).show(); - } else if (errorInfo.getThrowable() instanceof GeographicRestrictionException) { - Toast.makeText(context, R.string.georestricted_content, Toast.LENGTH_LONG).show(); - } else if (errorInfo.getThrowable() instanceof PaidContentException) { - Toast.makeText(context, R.string.paid_content, Toast.LENGTH_LONG).show(); - } else if (errorInfo.getThrowable() instanceof PrivateContentException) { - Toast.makeText(context, R.string.private_content, Toast.LENGTH_LONG).show(); - } else if (errorInfo.getThrowable() instanceof SoundCloudGoPlusContentException) { - Toast.makeText(context, R.string.soundcloud_go_plus_content, - Toast.LENGTH_LONG).show(); - } else if (errorInfo.getThrowable() instanceof YoutubeMusicPremiumContentException) { - Toast.makeText(context, R.string.youtube_music_premium_content, - Toast.LENGTH_LONG).show(); - } else if (errorInfo.getThrowable() instanceof ContentNotAvailableException) { - Toast.makeText(context, R.string.content_not_available, Toast.LENGTH_LONG).show(); - } else if (errorInfo.getThrowable() instanceof ContentNotSupportedException) { - Toast.makeText(context, R.string.content_not_supported, Toast.LENGTH_LONG).show(); + } else if (errorInfo.getThrowable() instanceof ContentNotAvailableException + || errorInfo.getThrowable() instanceof ContentNotSupportedException) { + // this exception does not usually indicate a problem that should be reported, + // so just show a toast instead of the notification + Toast.makeText(context, errorInfo.getMessageStringId(), Toast.LENGTH_LONG).show(); } else { ErrorUtil.createNotification(context, errorInfo); } diff --git a/app/src/main/java/org/schabi/newpipe/error/ErrorInfo.kt b/app/src/main/java/org/schabi/newpipe/error/ErrorInfo.kt index 6d8c1bd638c..014be540f69 100644 --- a/app/src/main/java/org/schabi/newpipe/error/ErrorInfo.kt +++ b/app/src/main/java/org/schabi/newpipe/error/ErrorInfo.kt @@ -3,14 +3,25 @@ package org.schabi.newpipe.error import android.os.Parcelable import androidx.annotation.StringRes import com.google.android.exoplayer2.ExoPlaybackException +import com.google.android.exoplayer2.upstream.HttpDataSource +import com.google.android.exoplayer2.upstream.Loader import kotlinx.parcelize.IgnoredOnParcel import kotlinx.parcelize.Parcelize import org.schabi.newpipe.R import org.schabi.newpipe.extractor.Info import org.schabi.newpipe.extractor.exceptions.AccountTerminatedException +import org.schabi.newpipe.extractor.exceptions.AgeRestrictedContentException import org.schabi.newpipe.extractor.exceptions.ContentNotAvailableException import org.schabi.newpipe.extractor.exceptions.ContentNotSupportedException import org.schabi.newpipe.extractor.exceptions.ExtractionException +import org.schabi.newpipe.extractor.exceptions.GeographicRestrictionException +import org.schabi.newpipe.extractor.exceptions.PaidContentException +import org.schabi.newpipe.extractor.exceptions.PrivateContentException +import org.schabi.newpipe.extractor.exceptions.ReCaptchaException +import org.schabi.newpipe.extractor.exceptions.SoundCloudGoPlusContentException +import org.schabi.newpipe.extractor.exceptions.UnsupportedContentInCountryException +import org.schabi.newpipe.extractor.exceptions.YoutubeMusicPremiumContentException +import org.schabi.newpipe.extractor.exceptions.YoutubeSignInConfirmNotBotException import org.schabi.newpipe.ktx.isNetworkRelated import org.schabi.newpipe.util.ServiceHelper @@ -91,11 +102,28 @@ class ErrorInfo( action: UserAction ): Int { return when { + // content not available exceptions throwable is AccountTerminatedException -> R.string.account_terminated + throwable is AgeRestrictedContentException -> R.string.restricted_video_no_stream + throwable is GeographicRestrictionException -> R.string.georestricted_content + throwable is PaidContentException -> R.string.paid_content + throwable is PrivateContentException -> R.string.private_content + throwable is SoundCloudGoPlusContentException -> R.string.soundcloud_go_plus_content + throwable is UnsupportedContentInCountryException -> R.string.unsupported_content_in_country + throwable is YoutubeMusicPremiumContentException -> R.string.youtube_music_premium_content + throwable is YoutubeSignInConfirmNotBotException -> R.string.youtube_sign_in_confirm_not_bot_error throwable is ContentNotAvailableException -> R.string.content_not_available - throwable != null && throwable.isNetworkRelated -> R.string.network_error + + // ReCaptchas should have already been handled elsewhere, + // but return an error message here just in case + throwable is ReCaptchaException -> R.string.recaptcha_request_toast + + // other extractor exceptions throwable is ContentNotSupportedException -> R.string.content_not_supported + throwable != null && throwable.isNetworkRelated -> R.string.network_error throwable is ExtractionException -> R.string.parsing_error + + // ExoPlayer exceptions throwable is ExoPlaybackException -> { when (throwable.type) { ExoPlaybackException.TYPE_SOURCE -> R.string.player_stream_failure @@ -103,13 +131,15 @@ class ErrorInfo( else -> R.string.player_unrecoverable_failure } } + + // user actions (in case the exception is unrecognizable) action == UserAction.UI_ERROR -> R.string.app_ui_crash action == UserAction.REQUESTED_COMMENTS -> R.string.error_unable_to_load_comments action == UserAction.SUBSCRIPTION_CHANGE -> R.string.subscription_change_failed action == UserAction.SUBSCRIPTION_UPDATE -> R.string.subscription_update_failed action == UserAction.LOAD_IMAGE -> R.string.could_not_load_thumbnails action == UserAction.DOWNLOAD_OPEN_DIALOG -> R.string.could_not_setup_download_menu - else -> R.string.general_error + else -> R.string.error_snackbar_message } } } diff --git a/app/src/main/java/org/schabi/newpipe/error/ErrorPanelHelper.kt b/app/src/main/java/org/schabi/newpipe/error/ErrorPanelHelper.kt index 14ec4114836..66d4d9fae8b 100644 --- a/app/src/main/java/org/schabi/newpipe/error/ErrorPanelHelper.kt +++ b/app/src/main/java/org/schabi/newpipe/error/ErrorPanelHelper.kt @@ -15,19 +15,12 @@ import io.reactivex.rxjava3.disposables.Disposable import org.schabi.newpipe.MainActivity import org.schabi.newpipe.R import org.schabi.newpipe.extractor.exceptions.AccountTerminatedException -import org.schabi.newpipe.extractor.exceptions.AgeRestrictedContentException import org.schabi.newpipe.extractor.exceptions.ContentNotAvailableException import org.schabi.newpipe.extractor.exceptions.ContentNotSupportedException -import org.schabi.newpipe.extractor.exceptions.GeographicRestrictionException -import org.schabi.newpipe.extractor.exceptions.PaidContentException -import org.schabi.newpipe.extractor.exceptions.PrivateContentException import org.schabi.newpipe.extractor.exceptions.ReCaptchaException -import org.schabi.newpipe.extractor.exceptions.SoundCloudGoPlusContentException -import org.schabi.newpipe.extractor.exceptions.YoutubeMusicPremiumContentException import org.schabi.newpipe.extractor.utils.Utils.isNullOrEmpty import org.schabi.newpipe.ktx.animate import org.schabi.newpipe.ktx.isInterruptedCaused -import org.schabi.newpipe.ktx.isNetworkRelated import org.schabi.newpipe.util.ServiceHelper import org.schabi.newpipe.util.external_communication.ShareUtils import java.util.concurrent.TimeUnit @@ -127,7 +120,7 @@ class ErrorPanelHelper( ErrorUtil.openActivity(context, errorInfo) } - errorTextView.setText(getExceptionDescription(errorInfo.throwable)) + errorTextView.setText(errorInfo.messageStringId) if (errorInfo.throwable !is ContentNotAvailableException && errorInfo.throwable !is ContentNotSupportedException @@ -192,27 +185,5 @@ class ErrorPanelHelper( companion object { val TAG: String = ErrorPanelHelper::class.simpleName!! val DEBUG: Boolean = MainActivity.DEBUG - - @StringRes - fun getExceptionDescription(throwable: Throwable?): Int { - return when (throwable) { - is AgeRestrictedContentException -> R.string.restricted_video_no_stream - is GeographicRestrictionException -> R.string.georestricted_content - is PaidContentException -> R.string.paid_content - is PrivateContentException -> R.string.private_content - is SoundCloudGoPlusContentException -> R.string.soundcloud_go_plus_content - is YoutubeMusicPremiumContentException -> R.string.youtube_music_premium_content - is ContentNotAvailableException -> R.string.content_not_available - is ContentNotSupportedException -> R.string.content_not_supported - else -> { - // show retry button only for content which is not unavailable or unsupported - if (throwable != null && throwable.isNetworkRelated) { - R.string.network_error - } else { - R.string.error_snackbar_message - } - } - } - } } } diff --git a/app/src/main/java/org/schabi/newpipe/error/ErrorUtil.kt b/app/src/main/java/org/schabi/newpipe/error/ErrorUtil.kt index e74711b88d2..958188b6abd 100644 --- a/app/src/main/java/org/schabi/newpipe/error/ErrorUtil.kt +++ b/app/src/main/java/org/schabi/newpipe/error/ErrorUtil.kt @@ -156,7 +156,7 @@ class ErrorUtil { // fallback to showing a notification if no root view is available createNotification(context, errorInfo) } else { - Snackbar.make(rootView, R.string.error_snackbar_message, Snackbar.LENGTH_LONG) + Snackbar.make(rootView, errorInfo.messageStringId, Snackbar.LENGTH_LONG) .setActionTextColor(Color.YELLOW) .setAction(context.getString(R.string.error_snackbar_action).uppercase()) { openActivity(context, errorInfo) diff --git a/app/src/main/java/org/schabi/newpipe/error/UserAction.java b/app/src/main/java/org/schabi/newpipe/error/UserAction.java index afb880a292a..997bff99629 100644 --- a/app/src/main/java/org/schabi/newpipe/error/UserAction.java +++ b/app/src/main/java/org/schabi/newpipe/error/UserAction.java @@ -33,7 +33,8 @@ public enum UserAction { SHARE_TO_NEWPIPE("share to newpipe"), CHECK_FOR_NEW_APP_VERSION("check for new app version"), OPEN_INFO_ITEM_DIALOG("open info item dialog"), - GETTING_MAIN_SCREEN_TAB("getting main screen tab"); + GETTING_MAIN_SCREEN_TAB("getting main screen tab"), + PLAY_ON_POPUP("play on popup"); private final String message; diff --git a/app/src/main/java/org/schabi/newpipe/util/text/InternalUrlsHandler.java b/app/src/main/java/org/schabi/newpipe/util/text/InternalUrlsHandler.java index 066515d6b96..a2743141bd3 100644 --- a/app/src/main/java/org/schabi/newpipe/util/text/InternalUrlsHandler.java +++ b/app/src/main/java/org/schabi/newpipe/util/text/InternalUrlsHandler.java @@ -1,14 +1,13 @@ package org.schabi.newpipe.util.text; import android.content.Context; -import android.util.Log; import androidx.annotation.NonNull; -import androidx.appcompat.app.AlertDialog; import org.schabi.newpipe.MainActivity; -import org.schabi.newpipe.R; -import org.schabi.newpipe.error.ErrorPanelHelper; +import org.schabi.newpipe.error.ErrorInfo; +import org.schabi.newpipe.error.ErrorUtil; +import org.schabi.newpipe.error.UserAction; import org.schabi.newpipe.extractor.NewPipe; import org.schabi.newpipe.extractor.StreamingService; import org.schabi.newpipe.extractor.exceptions.ExtractionException; @@ -158,19 +157,13 @@ public static boolean playOnPopup(final Context context, disposables.add(single.subscribeOn(Schedulers.io()) .observeOn(AndroidSchedulers.mainThread()) .subscribe(info -> { - final PlayQueue playQueue = - new SinglePlayQueue(info, seconds * 1000L); + final PlayQueue playQueue = new SinglePlayQueue(info, seconds * 1000L); NavigationHelper.playOnPopupPlayer(context, playQueue, false); }, throwable -> { - if (DEBUG) { - Log.e(TAG, "Could not play on popup: " + url, throwable); - } - new AlertDialog.Builder(context) - .setTitle(R.string.player_stream_failure) - .setMessage( - ErrorPanelHelper.Companion.getExceptionDescription(throwable)) - .setPositiveButton(R.string.ok, null) - .show(); + final var errorInfo = new ErrorInfo(throwable, UserAction.PLAY_ON_POPUP, url); + // This will only show a snackbar if the passed context has a root view: + // otherwise it will resort to showing a notification, so we are safe here. + ErrorUtil.showSnackbar(context, errorInfo); })); return true; } diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index 922b7bd3fd3..21593674dbb 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -877,4 +877,6 @@ Trending movies and shows Trending music Entry deleted + YouTube refused to provide data, asking for a login.\n\nYour IP might have been temporarily banned by YouTube, you can wait some time or switch to a different IP (for example by turning on/off a VPN, or by switching from WiFi to mobile data). + This content is not available for the currently selected content country.\n\nChange your selection from \"Settings > Content > Default content country\". From 29a3ca83b5b9c18c00a72a0dbfb2582a24f11f14 Mon Sep 17 00:00:00 2001 From: Stypox Date: Mon, 28 Jul 2025 23:57:55 +0200 Subject: [PATCH 2/7] Show better information about player errors --- .../org/schabi/newpipe/error/ErrorInfo.kt | 19 +++++++++++++------ .../MediaBrowserPlaybackPreparer.kt | 7 ++++--- app/src/main/res/values/strings.xml | 1 + 3 files changed, 18 insertions(+), 9 deletions(-) diff --git a/app/src/main/java/org/schabi/newpipe/error/ErrorInfo.kt b/app/src/main/java/org/schabi/newpipe/error/ErrorInfo.kt index 014be540f69..f4af65bbcb1 100644 --- a/app/src/main/java/org/schabi/newpipe/error/ErrorInfo.kt +++ b/app/src/main/java/org/schabi/newpipe/error/ErrorInfo.kt @@ -23,6 +23,8 @@ import org.schabi.newpipe.extractor.exceptions.UnsupportedContentInCountryExcept import org.schabi.newpipe.extractor.exceptions.YoutubeMusicPremiumContentException import org.schabi.newpipe.extractor.exceptions.YoutubeSignInConfirmNotBotException import org.schabi.newpipe.ktx.isNetworkRelated +import org.schabi.newpipe.player.mediasource.FailedMediaSource +import org.schabi.newpipe.player.resolver.PlaybackResolver import org.schabi.newpipe.util.ServiceHelper @Parcelize @@ -97,9 +99,9 @@ class ErrorInfo( if (info == null) SERVICE_NONE else ServiceHelper.getNameOfServiceById(info.serviceId) @StringRes - private fun getMessageStringId( + fun getMessageStringId( throwable: Throwable?, - action: UserAction + action: UserAction? ): Int { return when { // content not available exceptions @@ -123,14 +125,19 @@ class ErrorInfo( throwable != null && throwable.isNetworkRelated -> R.string.network_error throwable is ExtractionException -> R.string.parsing_error - // ExoPlayer exceptions + // player exceptions throwable is ExoPlaybackException -> { - when (throwable.type) { - ExoPlaybackException.TYPE_SOURCE -> R.string.player_stream_failure - ExoPlaybackException.TYPE_UNEXPECTED -> R.string.player_recoverable_failure + val cause = throwable.cause + when { + cause is HttpDataSource.InvalidResponseCodeException && cause.responseCode == 403 -> R.string.player_error_403 + cause is Loader.UnexpectedLoaderException && cause.cause is ExtractionException -> getMessageStringId(throwable, action) + throwable.type == ExoPlaybackException.TYPE_SOURCE -> R.string.player_stream_failure + throwable.type == ExoPlaybackException.TYPE_UNEXPECTED -> R.string.player_recoverable_failure else -> R.string.player_unrecoverable_failure } } + throwable is FailedMediaSource.FailedMediaSourceException -> getMessageStringId(throwable.cause, action) + throwable is PlaybackResolver.ResolverException -> R.string.player_stream_failure // user actions (in case the exception is unrecognizable) action == UserAction.UI_ERROR -> R.string.app_ui_crash diff --git a/app/src/main/java/org/schabi/newpipe/player/mediabrowser/MediaBrowserPlaybackPreparer.kt b/app/src/main/java/org/schabi/newpipe/player/mediabrowser/MediaBrowserPlaybackPreparer.kt index 2948eeaf8d1..7f0f9f8b6a3 100644 --- a/app/src/main/java/org/schabi/newpipe/player/mediabrowser/MediaBrowserPlaybackPreparer.kt +++ b/app/src/main/java/org/schabi/newpipe/player/mediabrowser/MediaBrowserPlaybackPreparer.kt @@ -17,6 +17,7 @@ import io.reactivex.rxjava3.schedulers.Schedulers import org.schabi.newpipe.MainActivity import org.schabi.newpipe.NewPipeDatabase import org.schabi.newpipe.R +import org.schabi.newpipe.error.ErrorInfo import org.schabi.newpipe.extractor.InfoItem.InfoType import org.schabi.newpipe.extractor.exceptions.ContentNotAvailableException import org.schabi.newpipe.extractor.linkhandler.ListLinkHandler @@ -84,7 +85,7 @@ class MediaBrowserPlaybackPreparer( }, { throwable -> Log.e(TAG, "Failed to start playback of media ID [$mediaId]", throwable) - onPrepareError() + onPrepareError(throwable) } ) } @@ -115,9 +116,9 @@ class MediaBrowserPlaybackPreparer( ) } - private fun onPrepareError() { + private fun onPrepareError(throwable: Throwable) { setMediaSessionError.accept( - ContextCompat.getString(context, R.string.error_snackbar_message), + ContextCompat.getString(context, ErrorInfo.getMessageStringId(throwable, null)), PlaybackStateCompat.ERROR_CODE_APP_ERROR ) } diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index 21593674dbb..a54ddb9eedf 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -877,6 +877,7 @@ Trending movies and shows Trending music Entry deleted + HTTP error 403 occurred while playing, likely caused by an IP ban or streaming URL deobfuscation issues YouTube refused to provide data, asking for a login.\n\nYour IP might have been temporarily banned by YouTube, you can wait some time or switch to a different IP (for example by turning on/off a VPN, or by switching from WiFi to mobile data). This content is not available for the currently selected content country.\n\nChange your selection from \"Settings > Content > Default content country\". From 1bde2dcd9fbcb3402e1b5c9b9c297816d102cb80 Mon Sep 17 00:00:00 2001 From: Stypox Date: Tue, 29 Jul 2025 00:31:54 +0200 Subject: [PATCH 3/7] Fix ordering of error messages conditions --- .../org/schabi/newpipe/error/ErrorInfo.kt | 39 ++++++++++--------- 1 file changed, 21 insertions(+), 18 deletions(-) diff --git a/app/src/main/java/org/schabi/newpipe/error/ErrorInfo.kt b/app/src/main/java/org/schabi/newpipe/error/ErrorInfo.kt index f4af65bbcb1..77f818b0080 100644 --- a/app/src/main/java/org/schabi/newpipe/error/ErrorInfo.kt +++ b/app/src/main/java/org/schabi/newpipe/error/ErrorInfo.kt @@ -104,6 +104,21 @@ class ErrorInfo( action: UserAction? ): Int { return when { + // player exceptions + // some may be IOException, so do these checks before isNetworkRelated! + throwable is ExoPlaybackException -> { + val cause = throwable.cause + when { + cause is HttpDataSource.InvalidResponseCodeException && cause.responseCode == 403 -> R.string.player_error_403 + cause is Loader.UnexpectedLoaderException && cause.cause is ExtractionException -> getMessageStringId(throwable, action) + throwable.type == ExoPlaybackException.TYPE_SOURCE -> R.string.player_stream_failure + throwable.type == ExoPlaybackException.TYPE_UNEXPECTED -> R.string.player_recoverable_failure + else -> R.string.player_unrecoverable_failure + } + } + throwable is FailedMediaSource.FailedMediaSourceException -> getMessageStringId(throwable.cause, action) + throwable is PlaybackResolver.ResolverException -> R.string.player_stream_failure + // content not available exceptions throwable is AccountTerminatedException -> R.string.account_terminated throwable is AgeRestrictedContentException -> R.string.restricted_video_no_stream @@ -116,30 +131,18 @@ class ErrorInfo( throwable is YoutubeSignInConfirmNotBotException -> R.string.youtube_sign_in_confirm_not_bot_error throwable is ContentNotAvailableException -> R.string.content_not_available + // other extractor exceptions + throwable is ContentNotSupportedException -> R.string.content_not_supported // ReCaptchas should have already been handled elsewhere, // but return an error message here just in case throwable is ReCaptchaException -> R.string.recaptcha_request_toast - - // other extractor exceptions - throwable is ContentNotSupportedException -> R.string.content_not_supported + // test this at the end as many exceptions could be a subclass of IOException throwable != null && throwable.isNetworkRelated -> R.string.network_error + // an extraction exception unrelated to the network + // is likely an issue with parsing the website throwable is ExtractionException -> R.string.parsing_error - // player exceptions - throwable is ExoPlaybackException -> { - val cause = throwable.cause - when { - cause is HttpDataSource.InvalidResponseCodeException && cause.responseCode == 403 -> R.string.player_error_403 - cause is Loader.UnexpectedLoaderException && cause.cause is ExtractionException -> getMessageStringId(throwable, action) - throwable.type == ExoPlaybackException.TYPE_SOURCE -> R.string.player_stream_failure - throwable.type == ExoPlaybackException.TYPE_UNEXPECTED -> R.string.player_recoverable_failure - else -> R.string.player_unrecoverable_failure - } - } - throwable is FailedMediaSource.FailedMediaSourceException -> getMessageStringId(throwable.cause, action) - throwable is PlaybackResolver.ResolverException -> R.string.player_stream_failure - - // user actions (in case the exception is unrecognizable) + // user actions (in case the exception is null or unrecognizable) action == UserAction.UI_ERROR -> R.string.app_ui_crash action == UserAction.REQUESTED_COMMENTS -> R.string.error_unable_to_load_comments action == UserAction.SUBSCRIPTION_CHANGE -> R.string.subscription_change_failed From a369deeef45b740e3dc4aca34ab23299fbe313e8 Mon Sep 17 00:00:00 2001 From: Stypox Date: Sat, 30 Aug 2025 14:33:04 +0200 Subject: [PATCH 4/7] Allow ErrorInfo messages with formatArgs - ErrorInfo.getMessage() now returns an ErrorMessage instance that can be formatted into a string using a context (this allows the construction of an ErrorInfo to remain independent of a Context) - now the service ID is used in ErrorInfo.getMessage() to customize some messages based on the currently selected service - player HTTP invalid statuses are now included in the message - building a custom error message for AccountTerminatedException was moved from ErrorPanelHelper to ErrorInfo --- app/build.gradle | 2 +- .../org/schabi/newpipe/RouterActivity.java | 2 +- .../newpipe/error/AcraReportSender.java | 2 +- .../schabi/newpipe/error/ErrorActivity.java | 2 +- .../org/schabi/newpipe/error/ErrorInfo.kt | 188 +++++++++++++----- .../schabi/newpipe/error/ErrorPanelHelper.kt | 19 +- .../org/schabi/newpipe/error/ErrorUtil.kt | 4 +- .../org/schabi/newpipe/error/UserAction.java | 3 +- .../SubscriptionsImportFragment.java | 2 +- .../MediaBrowserPlaybackPreparer.kt | 2 +- .../giga/ui/adapter/MissionAdapter.java | 6 +- app/src/main/res/values-ar-rLY/strings.xml | 1 - app/src/main/res/values-ar/strings.xml | 1 - app/src/main/res/values-az/strings.xml | 1 - app/src/main/res/values-be/strings.xml | 1 - app/src/main/res/values-bg/strings.xml | 1 - app/src/main/res/values-bn/strings.xml | 1 - app/src/main/res/values-ca/strings.xml | 1 - app/src/main/res/values-ckb/strings.xml | 1 - app/src/main/res/values-cs/strings.xml | 1 - app/src/main/res/values-da/strings.xml | 1 - app/src/main/res/values-de/strings.xml | 1 - app/src/main/res/values-el/strings.xml | 1 - app/src/main/res/values-eo/strings.xml | 1 - app/src/main/res/values-es/strings.xml | 1 - app/src/main/res/values-et/strings.xml | 1 - app/src/main/res/values-eu/strings.xml | 1 - app/src/main/res/values-fa/strings.xml | 1 - app/src/main/res/values-fi/strings.xml | 1 - app/src/main/res/values-fr/strings.xml | 1 - app/src/main/res/values-gl/strings.xml | 1 - app/src/main/res/values-he/strings.xml | 1 - app/src/main/res/values-hi/strings.xml | 1 - app/src/main/res/values-hr/strings.xml | 1 - app/src/main/res/values-hu/strings.xml | 1 - app/src/main/res/values-in/strings.xml | 1 - app/src/main/res/values-is/strings.xml | 1 - app/src/main/res/values-it/strings.xml | 1 - app/src/main/res/values-ja/strings.xml | 1 - app/src/main/res/values-ka/strings.xml | 1 - app/src/main/res/values-ko/strings.xml | 1 - app/src/main/res/values-lt/strings.xml | 1 - app/src/main/res/values-lv/strings.xml | 1 - app/src/main/res/values-mk/strings.xml | 1 - app/src/main/res/values-ml/strings.xml | 1 - app/src/main/res/values-nb-rNO/strings.xml | 1 - app/src/main/res/values-nl/strings.xml | 1 - app/src/main/res/values-nqo/strings.xml | 1 - app/src/main/res/values-or/strings.xml | 1 - app/src/main/res/values-pa/strings.xml | 1 - app/src/main/res/values-pl/strings.xml | 1 - app/src/main/res/values-pt-rBR/strings.xml | 1 - app/src/main/res/values-pt-rPT/strings.xml | 1 - app/src/main/res/values-pt/strings.xml | 1 - app/src/main/res/values-ro/strings.xml | 1 - app/src/main/res/values-ru/strings.xml | 1 - app/src/main/res/values-ryu/strings.xml | 1 - app/src/main/res/values-sat/strings.xml | 1 - app/src/main/res/values-sc/strings.xml | 1 - app/src/main/res/values-sk/strings.xml | 1 - app/src/main/res/values-so/strings.xml | 1 - app/src/main/res/values-sq/strings.xml | 1 - app/src/main/res/values-sr/strings.xml | 1 - app/src/main/res/values-sv/strings.xml | 1 - app/src/main/res/values-ta/strings.xml | 1 - app/src/main/res/values-tr/strings.xml | 1 - app/src/main/res/values-uk/strings.xml | 1 - app/src/main/res/values-vi/strings.xml | 1 - app/src/main/res/values-zh-rCN/strings.xml | 1 - app/src/main/res/values-zh-rHK/strings.xml | 1 - app/src/main/res/values-zh-rTW/strings.xml | 1 - app/src/main/res/values/strings.xml | 8 +- 72 files changed, 154 insertions(+), 146 deletions(-) diff --git a/app/build.gradle b/app/build.gradle index 7f4166a5754..38765476a23 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -214,7 +214,7 @@ dependencies { // the corresponding commit hash, since JitPack sometimes deletes artifacts. // If there’s already a git hash, just add more of it to the end (or remove a letter) // to cause jitpack to regenerate the artifact. - implementation 'com.github.Stypox:NewPipeExtractor:b8bd4cda8cca00a14940933e3d3635d5aafec222' + implementation 'com.github.TeamNewPipe:NewPipeExtractor:0023b22095a2d62a60cdfc87f4b5cd85c8b266c3' implementation 'com.github.TeamNewPipe:NoNonsense-FilePicker:5.0.0' /** Checkstyle **/ diff --git a/app/src/main/java/org/schabi/newpipe/RouterActivity.java b/app/src/main/java/org/schabi/newpipe/RouterActivity.java index dac2d29a126..cb7ea3dd7e6 100644 --- a/app/src/main/java/org/schabi/newpipe/RouterActivity.java +++ b/app/src/main/java/org/schabi/newpipe/RouterActivity.java @@ -276,7 +276,7 @@ private static void handleError(final Context context, final ErrorInfo errorInfo || errorInfo.getThrowable() instanceof ContentNotSupportedException) { // this exception does not usually indicate a problem that should be reported, // so just show a toast instead of the notification - Toast.makeText(context, errorInfo.getMessageStringId(), Toast.LENGTH_LONG).show(); + Toast.makeText(context, errorInfo.getMessage(context), Toast.LENGTH_LONG).show(); } else { ErrorUtil.createNotification(context, errorInfo); } diff --git a/app/src/main/java/org/schabi/newpipe/error/AcraReportSender.java b/app/src/main/java/org/schabi/newpipe/error/AcraReportSender.java index 4d99663643d..8876a66e4ce 100644 --- a/app/src/main/java/org/schabi/newpipe/error/AcraReportSender.java +++ b/app/src/main/java/org/schabi/newpipe/error/AcraReportSender.java @@ -36,7 +36,7 @@ public void send(@NonNull final Context context, @NonNull final CrashReportData ErrorUtil.openActivity(context, new ErrorInfo( new String[]{report.getString(ReportField.STACK_TRACE)}, UserAction.UI_ERROR, - ErrorInfo.SERVICE_NONE, + null, "ACRA report", R.string.app_ui_crash)); } diff --git a/app/src/main/java/org/schabi/newpipe/error/ErrorActivity.java b/app/src/main/java/org/schabi/newpipe/error/ErrorActivity.java index a07b9b0b5d9..160dcca4df4 100644 --- a/app/src/main/java/org/schabi/newpipe/error/ErrorActivity.java +++ b/app/src/main/java/org/schabi/newpipe/error/ErrorActivity.java @@ -115,7 +115,7 @@ protected void onCreate(final Bundle savedInstanceState) { // normal bugreport buildInfo(errorInfo); - activityErrorBinding.errorMessageView.setText(errorInfo.getMessageStringId()); + activityErrorBinding.errorMessageView.setText(errorInfo.getMessage(this)); activityErrorBinding.errorView.setText(formErrorText(errorInfo.getStackTraces())); // print stack trace once again for debugging: diff --git a/app/src/main/java/org/schabi/newpipe/error/ErrorInfo.kt b/app/src/main/java/org/schabi/newpipe/error/ErrorInfo.kt index 77f818b0080..bac294d0f5d 100644 --- a/app/src/main/java/org/schabi/newpipe/error/ErrorInfo.kt +++ b/app/src/main/java/org/schabi/newpipe/error/ErrorInfo.kt @@ -1,7 +1,9 @@ package org.schabi.newpipe.error +import android.content.Context import android.os.Parcelable import androidx.annotation.StringRes +import androidx.core.content.ContextCompat import com.google.android.exoplayer2.ExoPlaybackException import com.google.android.exoplayer2.upstream.HttpDataSource import com.google.android.exoplayer2.upstream.Loader @@ -9,6 +11,8 @@ import kotlinx.parcelize.IgnoredOnParcel import kotlinx.parcelize.Parcelize import org.schabi.newpipe.R import org.schabi.newpipe.extractor.Info +import org.schabi.newpipe.extractor.ServiceList +import org.schabi.newpipe.extractor.ServiceList.YouTube import org.schabi.newpipe.extractor.exceptions.AccountTerminatedException import org.schabi.newpipe.extractor.exceptions.AgeRestrictedContentException import org.schabi.newpipe.extractor.exceptions.ContentNotAvailableException @@ -18,22 +22,21 @@ import org.schabi.newpipe.extractor.exceptions.GeographicRestrictionException import org.schabi.newpipe.extractor.exceptions.PaidContentException import org.schabi.newpipe.extractor.exceptions.PrivateContentException import org.schabi.newpipe.extractor.exceptions.ReCaptchaException +import org.schabi.newpipe.extractor.exceptions.SignInConfirmNotBotException import org.schabi.newpipe.extractor.exceptions.SoundCloudGoPlusContentException import org.schabi.newpipe.extractor.exceptions.UnsupportedContentInCountryException import org.schabi.newpipe.extractor.exceptions.YoutubeMusicPremiumContentException -import org.schabi.newpipe.extractor.exceptions.YoutubeSignInConfirmNotBotException import org.schabi.newpipe.ktx.isNetworkRelated import org.schabi.newpipe.player.mediasource.FailedMediaSource import org.schabi.newpipe.player.resolver.PlaybackResolver -import org.schabi.newpipe.util.ServiceHelper @Parcelize -class ErrorInfo( +class ErrorInfo private constructor( val stackTraces: Array, val userAction: UserAction, - val serviceName: String, + val serviceId: Int?, val request: String, - val messageStringId: Int + private val message: ErrorMessage, ) : Parcelable { // no need to store throwable, all data for report is in other variables @@ -44,14 +47,14 @@ class ErrorInfo( private constructor( throwable: Throwable, userAction: UserAction, - serviceName: String, + serviceId: Int?, request: String ) : this( throwableToStringList(throwable), userAction, - serviceName, + serviceId, request, - getMessageStringId(throwable, userAction) + getMessage(throwable, userAction, serviceId) ) { this.throwable = throwable } @@ -59,97 +62,176 @@ class ErrorInfo( private constructor( throwable: List, userAction: UserAction, - serviceName: String, + serviceId: Int?, request: String ) : this( throwableListToStringList(throwable), userAction, - serviceName, + serviceId, request, - getMessageStringId(throwable.firstOrNull(), userAction) + getMessage(throwable.firstOrNull(), userAction, serviceId) ) { this.throwable = throwable.firstOrNull() } + // constructor to manually build ErrorInfo + constructor(stackTraces: Array, userAction: UserAction, serviceId: Int?, request: String, @StringRes message: Int) : + this(stackTraces, userAction, serviceId, request, ErrorMessage(message)) + // constructors with single throwable constructor(throwable: Throwable, userAction: UserAction, request: String) : - this(throwable, userAction, SERVICE_NONE, request) + this(throwable, userAction, null, request) constructor(throwable: Throwable, userAction: UserAction, request: String, serviceId: Int) : - this(throwable, userAction, ServiceHelper.getNameOfServiceById(serviceId), request) + this(throwable, userAction, serviceId, request) constructor(throwable: Throwable, userAction: UserAction, request: String, info: Info?) : - this(throwable, userAction, getInfoServiceName(info), request) + this(throwable, userAction, info?.serviceId, request) // constructors with list of throwables constructor(throwable: List, userAction: UserAction, request: String) : - this(throwable, userAction, SERVICE_NONE, request) + this(throwable, userAction, null, request) constructor(throwable: List, userAction: UserAction, request: String, serviceId: Int) : - this(throwable, userAction, ServiceHelper.getNameOfServiceById(serviceId), request) + this(throwable, userAction, serviceId, request) constructor(throwable: List, userAction: UserAction, request: String, info: Info?) : - this(throwable, userAction, getInfoServiceName(info), request) + this(throwable, userAction, info?.serviceId, request) + + fun getServiceName(): String { + return getServiceName(serviceId) + } + + fun getMessage(context: Context): String { + return message.getString(context) + } companion object { - const val SERVICE_NONE = "none" + @Parcelize + class ErrorMessage( + @StringRes + private val stringRes: Int, + private vararg val formatArgs: String, + ) : Parcelable { + fun getString(context: Context): String { + return if (formatArgs.isEmpty()) { + // use ContextCompat.getString() just in case context is not AppCompatActivity + ContextCompat.getString(context, stringRes) + } else { + // ContextCompat.getString() with formatArgs does not exist, so we just + // replicate its source code but with formatArgs + ContextCompat.getContextForLanguage(context).getString(stringRes, *formatArgs) + } + } + } + + const val SERVICE_NONE = "" + + private fun getServiceName(serviceId: Int?) = + // not using getNameOfServiceById since we want to accept a nullable serviceId and we + // want to default to SERVICE_NONE + ServiceList.all()?.firstOrNull { it.serviceId == serviceId }?.serviceInfo?.name + ?: SERVICE_NONE fun throwableToStringList(throwable: Throwable) = arrayOf(throwable.stackTraceToString()) fun throwableListToStringList(throwableList: List) = throwableList.map { it.stackTraceToString() }.toTypedArray() - private fun getInfoServiceName(info: Info?) = - if (info == null) SERVICE_NONE else ServiceHelper.getNameOfServiceById(info.serviceId) - - @StringRes - fun getMessageStringId( + fun getMessage( throwable: Throwable?, - action: UserAction? - ): Int { + action: UserAction?, + serviceId: Int?, + ): ErrorMessage { return when { // player exceptions // some may be IOException, so do these checks before isNetworkRelated! throwable is ExoPlaybackException -> { val cause = throwable.cause when { - cause is HttpDataSource.InvalidResponseCodeException && cause.responseCode == 403 -> R.string.player_error_403 - cause is Loader.UnexpectedLoaderException && cause.cause is ExtractionException -> getMessageStringId(throwable, action) - throwable.type == ExoPlaybackException.TYPE_SOURCE -> R.string.player_stream_failure - throwable.type == ExoPlaybackException.TYPE_UNEXPECTED -> R.string.player_recoverable_failure - else -> R.string.player_unrecoverable_failure + cause is HttpDataSource.InvalidResponseCodeException -> { + if (cause.responseCode == 403) { + if (serviceId == YouTube.serviceId) { + ErrorMessage(R.string.youtube_player_http_403) + } else { + ErrorMessage(R.string.player_http_403) + } + } else { + ErrorMessage(R.string.player_http_invalid_status, cause.responseCode.toString()) + } + } + cause is Loader.UnexpectedLoaderException && cause.cause is ExtractionException -> + getMessage(throwable, action, serviceId) + throwable.type == ExoPlaybackException.TYPE_SOURCE -> + ErrorMessage(R.string.player_stream_failure) + throwable.type == ExoPlaybackException.TYPE_UNEXPECTED -> + ErrorMessage(R.string.player_recoverable_failure) + else -> + ErrorMessage(R.string.player_unrecoverable_failure) } } - throwable is FailedMediaSource.FailedMediaSourceException -> getMessageStringId(throwable.cause, action) - throwable is PlaybackResolver.ResolverException -> R.string.player_stream_failure + throwable is FailedMediaSource.FailedMediaSourceException -> + getMessage(throwable.cause, action, serviceId) + throwable is PlaybackResolver.ResolverException -> + ErrorMessage(R.string.player_stream_failure) // content not available exceptions - throwable is AccountTerminatedException -> R.string.account_terminated - throwable is AgeRestrictedContentException -> R.string.restricted_video_no_stream - throwable is GeographicRestrictionException -> R.string.georestricted_content - throwable is PaidContentException -> R.string.paid_content - throwable is PrivateContentException -> R.string.private_content - throwable is SoundCloudGoPlusContentException -> R.string.soundcloud_go_plus_content - throwable is UnsupportedContentInCountryException -> R.string.unsupported_content_in_country - throwable is YoutubeMusicPremiumContentException -> R.string.youtube_music_premium_content - throwable is YoutubeSignInConfirmNotBotException -> R.string.youtube_sign_in_confirm_not_bot_error - throwable is ContentNotAvailableException -> R.string.content_not_available + throwable is AccountTerminatedException -> + throwable.message + ?.takeIf { reason -> !reason.isEmpty() } + ?.let { reason -> + ErrorMessage( + R.string.account_terminated_service_provides_reason, + getServiceName(serviceId), + reason + ) + } + ?: ErrorMessage(R.string.account_terminated) + throwable is AgeRestrictedContentException -> + ErrorMessage(R.string.restricted_video_no_stream) + throwable is GeographicRestrictionException -> + ErrorMessage(R.string.georestricted_content) + throwable is PaidContentException -> + ErrorMessage(R.string.paid_content) + throwable is PrivateContentException -> + ErrorMessage(R.string.private_content) + throwable is SoundCloudGoPlusContentException -> + ErrorMessage(R.string.soundcloud_go_plus_content) + throwable is UnsupportedContentInCountryException -> + ErrorMessage(R.string.unsupported_content_in_country) + throwable is YoutubeMusicPremiumContentException -> + ErrorMessage(R.string.youtube_music_premium_content) + throwable is SignInConfirmNotBotException -> + ErrorMessage(R.string.sign_in_confirm_not_bot_error, getServiceName(serviceId)) + throwable is ContentNotAvailableException -> + ErrorMessage(R.string.content_not_available) // other extractor exceptions - throwable is ContentNotSupportedException -> R.string.content_not_supported + throwable is ContentNotSupportedException -> + ErrorMessage(R.string.content_not_supported) // ReCaptchas should have already been handled elsewhere, // but return an error message here just in case - throwable is ReCaptchaException -> R.string.recaptcha_request_toast + throwable is ReCaptchaException -> + ErrorMessage(R.string.recaptcha_request_toast) // test this at the end as many exceptions could be a subclass of IOException - throwable != null && throwable.isNetworkRelated -> R.string.network_error + throwable != null && throwable.isNetworkRelated -> + ErrorMessage(R.string.network_error) // an extraction exception unrelated to the network // is likely an issue with parsing the website - throwable is ExtractionException -> R.string.parsing_error + throwable is ExtractionException -> + ErrorMessage(R.string.parsing_error) // user actions (in case the exception is null or unrecognizable) - action == UserAction.UI_ERROR -> R.string.app_ui_crash - action == UserAction.REQUESTED_COMMENTS -> R.string.error_unable_to_load_comments - action == UserAction.SUBSCRIPTION_CHANGE -> R.string.subscription_change_failed - action == UserAction.SUBSCRIPTION_UPDATE -> R.string.subscription_update_failed - action == UserAction.LOAD_IMAGE -> R.string.could_not_load_thumbnails - action == UserAction.DOWNLOAD_OPEN_DIALOG -> R.string.could_not_setup_download_menu - else -> R.string.error_snackbar_message + action == UserAction.UI_ERROR -> + ErrorMessage(R.string.app_ui_crash) + action == UserAction.REQUESTED_COMMENTS -> + ErrorMessage(R.string.error_unable_to_load_comments) + action == UserAction.SUBSCRIPTION_CHANGE -> + ErrorMessage(R.string.subscription_change_failed) + action == UserAction.SUBSCRIPTION_UPDATE -> + ErrorMessage(R.string.subscription_update_failed) + action == UserAction.LOAD_IMAGE -> + ErrorMessage(R.string.could_not_load_thumbnails) + action == UserAction.DOWNLOAD_OPEN_DIALOG -> + ErrorMessage(R.string.could_not_setup_download_menu) + else -> + ErrorMessage(R.string.error_snackbar_message) } } } diff --git a/app/src/main/java/org/schabi/newpipe/error/ErrorPanelHelper.kt b/app/src/main/java/org/schabi/newpipe/error/ErrorPanelHelper.kt index 66d4d9fae8b..9597591275a 100644 --- a/app/src/main/java/org/schabi/newpipe/error/ErrorPanelHelper.kt +++ b/app/src/main/java/org/schabi/newpipe/error/ErrorPanelHelper.kt @@ -14,14 +14,11 @@ import io.reactivex.rxjava3.android.schedulers.AndroidSchedulers import io.reactivex.rxjava3.disposables.Disposable import org.schabi.newpipe.MainActivity import org.schabi.newpipe.R -import org.schabi.newpipe.extractor.exceptions.AccountTerminatedException import org.schabi.newpipe.extractor.exceptions.ContentNotAvailableException import org.schabi.newpipe.extractor.exceptions.ContentNotSupportedException import org.schabi.newpipe.extractor.exceptions.ReCaptchaException -import org.schabi.newpipe.extractor.utils.Utils.isNullOrEmpty import org.schabi.newpipe.ktx.animate import org.schabi.newpipe.ktx.isInterruptedCaused -import org.schabi.newpipe.util.ServiceHelper import org.schabi.newpipe.util.external_communication.ShareUtils import java.util.concurrent.TimeUnit @@ -99,20 +96,6 @@ class ErrorPanelHelper( errorRetryButton.isVisible = retryShouldBeShown showAndSetOpenInBrowserButtonAction(errorInfo) - } else if (errorInfo.throwable is AccountTerminatedException) { - errorTextView.setText(R.string.account_terminated) - - if (!isNullOrEmpty((errorInfo.throwable as AccountTerminatedException).message)) { - errorServiceInfoTextView.text = context.resources.getString( - R.string.service_provides_reason, - ServiceHelper.getSelectedService(context)?.serviceInfo?.name ?: "" - ) - errorServiceInfoTextView.isVisible = true - - errorServiceExplanationTextView.text = - (errorInfo.throwable as AccountTerminatedException).message - errorServiceExplanationTextView.isVisible = true - } } else { showAndSetErrorButtonAction( R.string.error_snackbar_action @@ -120,7 +103,7 @@ class ErrorPanelHelper( ErrorUtil.openActivity(context, errorInfo) } - errorTextView.setText(errorInfo.messageStringId) + errorTextView.text = errorInfo.getMessage(context) if (errorInfo.throwable !is ContentNotAvailableException && errorInfo.throwable !is ContentNotSupportedException diff --git a/app/src/main/java/org/schabi/newpipe/error/ErrorUtil.kt b/app/src/main/java/org/schabi/newpipe/error/ErrorUtil.kt index 958188b6abd..520d02b3be4 100644 --- a/app/src/main/java/org/schabi/newpipe/error/ErrorUtil.kt +++ b/app/src/main/java/org/schabi/newpipe/error/ErrorUtil.kt @@ -122,7 +122,7 @@ class ErrorUtil { ) .setSmallIcon(R.drawable.ic_bug_report) .setContentTitle(context.getString(R.string.error_report_notification_title)) - .setContentText(context.getString(errorInfo.messageStringId)) + .setContentText(errorInfo.getMessage(context)) .setAutoCancel(true) .setContentIntent( PendingIntentCompat.getActivity( @@ -156,7 +156,7 @@ class ErrorUtil { // fallback to showing a notification if no root view is available createNotification(context, errorInfo) } else { - Snackbar.make(rootView, errorInfo.messageStringId, Snackbar.LENGTH_LONG) + Snackbar.make(rootView, errorInfo.getMessage(context), Snackbar.LENGTH_LONG) .setActionTextColor(Color.YELLOW) .setAction(context.getString(R.string.error_snackbar_action).uppercase()) { openActivity(context, errorInfo) diff --git a/app/src/main/java/org/schabi/newpipe/error/UserAction.java b/app/src/main/java/org/schabi/newpipe/error/UserAction.java index 997bff99629..64829523a8f 100644 --- a/app/src/main/java/org/schabi/newpipe/error/UserAction.java +++ b/app/src/main/java/org/schabi/newpipe/error/UserAction.java @@ -34,7 +34,8 @@ public enum UserAction { CHECK_FOR_NEW_APP_VERSION("check for new app version"), OPEN_INFO_ITEM_DIALOG("open info item dialog"), GETTING_MAIN_SCREEN_TAB("getting main screen tab"), - PLAY_ON_POPUP("play on popup"); + PLAY_ON_POPUP("play on popup"), + SUBSCRIPTIONS("loading subscriptions"),; private final String message; diff --git a/app/src/main/java/org/schabi/newpipe/local/subscription/SubscriptionsImportFragment.java b/app/src/main/java/org/schabi/newpipe/local/subscription/SubscriptionsImportFragment.java index 77a70afa9dc..501639ff8f9 100644 --- a/app/src/main/java/org/schabi/newpipe/local/subscription/SubscriptionsImportFragment.java +++ b/app/src/main/java/org/schabi/newpipe/local/subscription/SubscriptionsImportFragment.java @@ -89,7 +89,7 @@ public void onCreate(final Bundle savedInstanceState) { if (supportedSources.isEmpty() && currentServiceId != Constants.NO_SERVICE_ID) { ErrorUtil.showSnackbar(activity, new ErrorInfo(new String[]{}, UserAction.SUBSCRIPTION_IMPORT_EXPORT, - ServiceHelper.getNameOfServiceById(currentServiceId), + currentServiceId, "Service does not support importing subscriptions", R.string.general_error)); activity.finish(); diff --git a/app/src/main/java/org/schabi/newpipe/player/mediabrowser/MediaBrowserPlaybackPreparer.kt b/app/src/main/java/org/schabi/newpipe/player/mediabrowser/MediaBrowserPlaybackPreparer.kt index 7f0f9f8b6a3..4815965a368 100644 --- a/app/src/main/java/org/schabi/newpipe/player/mediabrowser/MediaBrowserPlaybackPreparer.kt +++ b/app/src/main/java/org/schabi/newpipe/player/mediabrowser/MediaBrowserPlaybackPreparer.kt @@ -118,7 +118,7 @@ class MediaBrowserPlaybackPreparer( private fun onPrepareError(throwable: Throwable) { setMediaSessionError.accept( - ContextCompat.getString(context, ErrorInfo.getMessageStringId(throwable, null)), + ErrorInfo.getMessage(throwable, null, null).getString(context), PlaybackStateCompat.ERROR_CODE_APP_ERROR ) } diff --git a/app/src/main/java/us/shandian/giga/ui/adapter/MissionAdapter.java b/app/src/main/java/us/shandian/giga/ui/adapter/MissionAdapter.java index 79dda9011de..31065d57c6a 100644 --- a/app/src/main/java/us/shandian/giga/ui/adapter/MissionAdapter.java +++ b/app/src/main/java/us/shandian/giga/ui/adapter/MissionAdapter.java @@ -563,11 +563,11 @@ private void showError(DownloadMission mission, UserAction action, @StringRes in } request.append("]"); - String service; + Integer service; try { - service = NewPipe.getServiceByUrl(mission.source).getServiceInfo().getName(); + service = NewPipe.getServiceByUrl(mission.source).getServiceId(); } catch (Exception e) { - service = ErrorInfo.SERVICE_NONE; + service = null; } ErrorUtil.createNotification(mContext, diff --git a/app/src/main/res/values-ar-rLY/strings.xml b/app/src/main/res/values-ar-rLY/strings.xml index 7f881a9c2a6..35e6cb5e790 100644 --- a/app/src/main/res/values-ar-rLY/strings.xml +++ b/app/src/main/res/values-ar-rLY/strings.xml @@ -641,7 +641,6 @@ الصوت : %s خطوة حل - %s يقدم هذا السبب: الدفق المحدد غير مدعوم من قبل المشغلون الخارجيون عن تطبيق نيوپايپ تسريع إلى الأمام/-ترجيع وقت البحث diff --git a/app/src/main/res/values-ar/strings.xml b/app/src/main/res/values-ar/strings.xml index 7865b1f9d70..f5c8efb0df2 100644 --- a/app/src/main/res/values-ar/strings.xml +++ b/app/src/main/res/values-ar/strings.xml @@ -649,7 +649,6 @@ تمكين تحديد نص في الوصف يمكنك الآن تحديد نص داخل الوصف. لاحظ أن الصفحة قد تومض وقد لا تكون الروابط قابلة للنقر أثناء وضع التحديد. فتح الموقع - %s يقدم هذا السبب: تم إنهاء الحساب لا يوفر وضع التغذية السريعة مزيدًا من المعلومات حول هذا الموضوع. حساب منشئ المحتوى قد تم إنهائه. diff --git a/app/src/main/res/values-az/strings.xml b/app/src/main/res/values-az/strings.xml index 78cb6c0130a..0e0135c716d 100644 --- a/app/src/main/res/values-az/strings.xml +++ b/app/src/main/res/values-az/strings.xml @@ -501,7 +501,6 @@ Endirmə növbəsini məhdudlaşdır Eyni vaxtda ancaq bir endirmə həyata keçiriləcək Hesab ləğv edildi - %s bu səbəbi təmin edir: Yükləmə başladı Açıqlamadakı mətni seçməyi qeyri-aktiv et Kateqoriya diff --git a/app/src/main/res/values-be/strings.xml b/app/src/main/res/values-be/strings.xml index a0930a9f8f7..72b08414e4f 100644 --- a/app/src/main/res/values-be/strings.xml +++ b/app/src/main/res/values-be/strings.xml @@ -704,7 +704,6 @@ Гэта змесціва з\'яўляецца прыватным, таму NewPipe не можа яго трансляваць або спампоўваць. Гэта відэа даступна толькі для падпісчыкаў YouTube Music Premium, таму NewPipe не можа яго трансляваць або спампоўваць. Уліковы запіс спынены - %s дае наступную прычыну: Вартае ўвагі Унутраная Прагледжаныя цалкам diff --git a/app/src/main/res/values-bg/strings.xml b/app/src/main/res/values-bg/strings.xml index 7ecab17c640..870b6be7940 100644 --- a/app/src/main/res/values-bg/strings.xml +++ b/app/src/main/res/values-bg/strings.xml @@ -416,7 +416,6 @@ Страница на плейлиста Глави Лиценз - %s посочва следната причина: Маркери Поверителност Език diff --git a/app/src/main/res/values-bn/strings.xml b/app/src/main/res/values-bn/strings.xml index 5721f12ee17..682b59fe3d7 100644 --- a/app/src/main/res/values-bn/strings.xml +++ b/app/src/main/res/values-bn/strings.xml @@ -540,7 +540,6 @@ \'%s\' এর জন্য ফিড প্রক্রিয়া করা যাচ্ছে না। বর্ণনার লেখা নির্বাচন করা নিষ্ক্রিয় করো বর্ণনার লেখা নির্বাচন করা সক্ষম করো - %s এই কারণ বলছে: প্রক্রিয়াকরণ ফিডে ত্রুটি ওয়েবসাইট খুলুন অ্যাকাউন্ট ধ্বংসকৃত diff --git a/app/src/main/res/values-ca/strings.xml b/app/src/main/res/values-ca/strings.xml index 819c9ff0b4e..dadac3c3f7d 100644 --- a/app/src/main/res/values-ca/strings.xml +++ b/app/src/main/res/values-ca/strings.xml @@ -612,7 +612,6 @@ Pot seleccionar el seu tema fosc favorit aqui sota Selecciona el teu tema fosc favorit — %s Automàtic (tema del dispositiu) - %s dóna aquesta raó: Usuari suspes El compte de l\'autor ha estat esborrat. \nNewPipe no serà capaç de carregar aquest fil en el futur. diff --git a/app/src/main/res/values-ckb/strings.xml b/app/src/main/res/values-ckb/strings.xml index 7c23d1d1d09..f0ddfb6e952 100644 --- a/app/src/main/res/values-ckb/strings.xml +++ b/app/src/main/res/values-ckb/strings.xml @@ -596,7 +596,6 @@ ڕادیۆ تایبەتکراو ئه‌م بابه‌ته‌ ته‌نیا بۆ ئه‌و كه‌سانه‌ به‌رده‌سته‌ كه‌ پاره‌یان داوه‌ ، بۆیه‌ ناتوانرێت له‌ نیوپایپه‌وه‌ داببه‌زێنرێت. - %s ئه‌م هۆكاره‌ دابین ده‌كات: هه‌ژمار له‌ناوبراوه‌ ئه‌م ڤیدیۆیه‌ ته‌نیا له‌ وه‌شانی نایابی یوتوب میوزیك به‌رده‌سته‌ ، بۆیه‌ ناتوانرێت له‌ نیوپایپه‌وه‌ داببه‌زێنرێت. ئه‌مه‌ تراكی SoundCloud Go+ ه‌ ، لانی كه‌م له‌ وڵاته‌كه‌ی تۆدا، ناتوانرێت له‌لایه‌ن نیوپایپه‌وه‌ داببه‌زێنرێت. diff --git a/app/src/main/res/values-cs/strings.xml b/app/src/main/res/values-cs/strings.xml index 2eabe57b047..756cf17cf13 100644 --- a/app/src/main/res/values-cs/strings.xml +++ b/app/src/main/res/values-cs/strings.xml @@ -619,7 +619,6 @@ Vypnout výběr textu v popisu Zapnout výběr textu v popisu Nyní můžete vybrat v popisu text. Pamatujte, že v režimu výběru může stránka blikat a odkazy nemusí reagovat na kliknutí. - %s udává teno důvod: Účet uzavřen Režim rychlého feedu o tom neposkytuje více informací. Autorův účet byl uzavřen. diff --git a/app/src/main/res/values-da/strings.xml b/app/src/main/res/values-da/strings.xml index db464ca61ea..5354bb7adfd 100644 --- a/app/src/main/res/values-da/strings.xml +++ b/app/src/main/res/values-da/strings.xml @@ -554,7 +554,6 @@ Dette indhold er privat, så det kan ikke streames eller hentes af NewPipe. Nyligt tilføjede Fremhævede - %s giver denne grund: %s lytter %s lyttere diff --git a/app/src/main/res/values-de/strings.xml b/app/src/main/res/values-de/strings.xml index 3e7adfcd9ae..b99209f0fcc 100644 --- a/app/src/main/res/values-de/strings.xml +++ b/app/src/main/res/values-de/strings.xml @@ -627,7 +627,6 @@ Du wirst jedes Mal gefragt werden, wohin der Download gespeichert werden soll Fehler beim Laden des Feeds Konnte Feed für \'%s\' nicht laden. - %s gibt diesen Grund an: An Tablet-Modus Aus diff --git a/app/src/main/res/values-el/strings.xml b/app/src/main/res/values-el/strings.xml index 0781776d76f..5cb645bfad1 100644 --- a/app/src/main/res/values-el/strings.xml +++ b/app/src/main/res/values-el/strings.xml @@ -608,7 +608,6 @@ Ενεργοποίηση επιλογής κειμένου στην περιγραφή Τώρα μπορείτε να επιλέξετε κείμενο εντός της περιγραφής. Σημειώστε ότι, η σελίδα μπορεί να παρουσιάζει αστάθεια κατά τη διάρκεια της κατάστασης επιλογής κειμένου. Ανοικτή ιστοσελίδα - Το %s παρέχει αυτή την αιτία: Ο λογαριασμός διαγράφηκε Η κατάσταση γρήγορης τροφοδοσίας δεν παρέχει περισσότερες πληροφορίες. Ο λογαριασμός του δημιουργού έχει διαγραφεί. diff --git a/app/src/main/res/values-eo/strings.xml b/app/src/main/res/values-eo/strings.xml index 408035e008c..3dde6961882 100644 --- a/app/src/main/res/values-eo/strings.xml +++ b/app/src/main/res/values-eo/strings.xml @@ -504,7 +504,6 @@ Ŝaltita Etikedoj Elŝutado komenciĝis - %s donas tiun kialon: Tiu enaĵo ne disponeblas en via lando. Freŝaj De %s diff --git a/app/src/main/res/values-es/strings.xml b/app/src/main/res/values-es/strings.xml index a1ee4f092c3..c88da0a2fb5 100644 --- a/app/src/main/res/values-es/strings.xml +++ b/app/src/main/res/values-es/strings.xml @@ -611,7 +611,6 @@ Deshabilitar la selección de texto de la descripción Habilitar la selección de texto de la descripción Ahora puede seleccionar el texto dentro de la descripción. Note que la página puede parpadear y los links no serán cliqueables mientras está en el modo de selección. - %s da esta razón: No fue posible cargar el feed por \'%s\'. Cuenta cancelada El modo de muro rápido no arroja más información sobre esto. diff --git a/app/src/main/res/values-et/strings.xml b/app/src/main/res/values-et/strings.xml index d25229cd03d..dc964367860 100644 --- a/app/src/main/res/values-et/strings.xml +++ b/app/src/main/res/values-et/strings.xml @@ -562,7 +562,6 @@ Näita pisipilte Kasuta pisipilti nii lukustusvaate kui teavituste taustana Kasutajakonto on suletud - %s toob põhjuseks: Võimalda valida kirjelduse teksti Ära võimalda valida kirjelduse teksti Kategooria diff --git a/app/src/main/res/values-eu/strings.xml b/app/src/main/res/values-eu/strings.xml index 20a7148ebd0..5c963d6b75d 100644 --- a/app/src/main/res/values-eu/strings.xml +++ b/app/src/main/res/values-eu/strings.xml @@ -615,7 +615,6 @@ Non gorde galdetuko zaizu deskarga bakoitzean Ez da deskargatzeko karpetarik ezarri oraindik, aukeratu lehenetsitako deskargatzeko karpeta orain Pribatutasuna - %s arrazoi hau ematen du: Kontua ezabatu da Jario azkarrak ez du honi buruz informazio gehiagorik ematen. Adin muga diff --git a/app/src/main/res/values-fa/strings.xml b/app/src/main/res/values-fa/strings.xml index 8b8fdd281b3..403fb4c11c0 100644 --- a/app/src/main/res/values-fa/strings.xml +++ b/app/src/main/res/values-fa/strings.xml @@ -626,7 +626,6 @@ \nنیوپایپ قادر به بار کردن این خوراک در آینده نیست. \nمی‌خواهید اشتراک این کانال را لغو کنید؟ حالت خوراک سریع، اطَلاعات بیش‌تری در این باره نمی‌دهد. - %s این دلیل را آورد: پیش‌نمایش بندانگشتی نوار جویش قلب‌شده به دست ایجادگر پیشنهادهای جست‌وجوی محلّی diff --git a/app/src/main/res/values-fi/strings.xml b/app/src/main/res/values-fi/strings.xml index 0c092284ceb..22c1fab120b 100644 --- a/app/src/main/res/values-fi/strings.xml +++ b/app/src/main/res/values-fi/strings.xml @@ -592,7 +592,6 @@ Yöteema Poista käytöstä tekstinvalinta kuvauskentän sisältä Voit nyt valita tekstin kuvauskentän sisältä. Huomioithan, että valintatilan aikana sivu voi vilkkua ja linkit eivät ehkä ole klikattavia. - %s tuo tämän syyn: Säätövivun kuvakkeen esikatselu Poista median tunnelointi käytöstä, jos havaitset mustan näyttöruudun tai änkytystä videon toistossa. Poista median tunnelointi käytöstä diff --git a/app/src/main/res/values-fr/strings.xml b/app/src/main/res/values-fr/strings.xml index 9cf8c6b2b6d..ffb78e19f48 100644 --- a/app/src/main/res/values-fr/strings.xml +++ b/app/src/main/res/values-fr/strings.xml @@ -620,7 +620,6 @@ Étiquettes Catégorie Vous pouvez maintenant sélectionner du texte à l’intérieur de la description. Notez que la page peut scintiller et que les liens peuvent ne pas être cliquables en mode sélection. - %s indique le motif : Aucun dossier de téléchargement n’est défini pour le moment, sélectionnez le dossier de téléchargement par défaut Ouvrir le site web Compte résilié diff --git a/app/src/main/res/values-gl/strings.xml b/app/src/main/res/values-gl/strings.xml index 3d98682bed9..aacaf9288c4 100644 --- a/app/src/main/res/values-gl/strings.xml +++ b/app/src/main/res/values-gl/strings.xml @@ -554,7 +554,6 @@ Agora pode seleccionar o texto na descrición. Teña en conta que a páxina pode cintilar e as ligazóns poden non ser clicábeis no modo selección. Automático (Tema do dispositivo) Radio - %s dá este motivo: Este contido non está dispoñíbel no seu país. Capítulos Recentes diff --git a/app/src/main/res/values-he/strings.xml b/app/src/main/res/values-he/strings.xml index 4553679ac7e..2131dc9c01e 100644 --- a/app/src/main/res/values-he/strings.xml +++ b/app/src/main/res/values-he/strings.xml @@ -632,7 +632,6 @@ \nל־NewPipe לא תהיה אפשרות להוריד את ההזנה הזאת בעתיד. \nלהסיר את המינוי מהערוץ הזה\? פתיחת האתר - %s מספק את הסיבה הבאה: החשבון הושמד מצב ההזנה המהירה לא מספק מידע נוסף על כך. לא ניתן לטעון את ההזנה עבור ‚%s’. diff --git a/app/src/main/res/values-hi/strings.xml b/app/src/main/res/values-hi/strings.xml index e4484742bcf..dd23cfc08f2 100644 --- a/app/src/main/res/values-hi/strings.xml +++ b/app/src/main/res/values-hi/strings.xml @@ -655,7 +655,6 @@ मीडिया टनलिंग अक्षम करें \"क्रैश द प्लेयर\" दिखाएं लोड नहीं हुआ: %d - %s इसका कारण प्रदान करता है: टैग लाइसेंस यदि आपको ऐप का उपयोग करने में परेशानी हो रही है, तो सामान्य प्रश्नों के इन उत्तरों को देखना सुनिश्चित करें! diff --git a/app/src/main/res/values-hr/strings.xml b/app/src/main/res/values-hr/strings.xml index 414fdf185a6..77a256ba425 100644 --- a/app/src/main/res/values-hr/strings.xml +++ b/app/src/main/res/values-hr/strings.xml @@ -639,7 +639,6 @@ Interno Privatnost Sada možeš odabrati tekst u opisu. Napomena: stranica će možda treperiti i možda nećeš moći kliknuti poveznice u načinu rada za odabir teksta. - %s pruža ovaj razlog: Obrada u tijeku … Može malo potrajati Za ukljanjanje stavki povuci ih Prikaži indikatore slike diff --git a/app/src/main/res/values-hu/strings.xml b/app/src/main/res/values-hu/strings.xml index d196268e28d..cf0e9da0420 100644 --- a/app/src/main/res/values-hu/strings.xml +++ b/app/src/main/res/values-hu/strings.xml @@ -537,7 +537,6 @@ Kapcsolódó elemek Ellenőrizze, hogy létezik-e már olyan jegy, amely az összeomlásával foglalkozik. Ha duplikált jegyet ad fel, akkor olyan időt vesz el tőlünk, amelyet a hiba javítására tudnánk fordítani. Minimalizálás alkalmazásváltáskor - A(z) %s ezt az okot adta meg: Helyi keresési javaslatok Távoli keresési javaslatok A fő lejátszó teljes képernyős indítása diff --git a/app/src/main/res/values-in/strings.xml b/app/src/main/res/values-in/strings.xml index 72316eff98c..3c3f0319207 100644 --- a/app/src/main/res/values-in/strings.xml +++ b/app/src/main/res/values-in/strings.xml @@ -599,7 +599,6 @@ Aktifkan dapat memilih teks pada deskripsi Anda sekarang dapat memilih teks di dalam deskripsi. Perhatikan bahwa halaman mungkin berkedip dan tautan tidak dapat diklik saat dalam mode pemilihan. Buka situs web - %s menyediakan alasan ini: Akun dinonaktifkan Mode langganan cepat tidak menyediakan lebih banyak info tentang ini. Akun kreator telah dinonaktifkan. diff --git a/app/src/main/res/values-is/strings.xml b/app/src/main/res/values-is/strings.xml index 936705ccf2f..9daa67dbf20 100644 --- a/app/src/main/res/values-is/strings.xml +++ b/app/src/main/res/values-is/strings.xml @@ -573,7 +573,6 @@ Enginn viðeigandi skráarstjóri fannst fyrir þessa aðgerð. \nVinsamlegast settu upp skráarstjóra sem styður Geymsluaðgangsramma (SAF) Þetta efni er ekki fáanlegt í þínu landi. - %s gefur þessa ástæðu: Þetta efni er aðeins í boði fyrir notendur sem hafa greitt — það er ekki hægt að streyma því eða sækja með NewPipe. Sjálfvirk (þema tækis) Veldu uppáhalds næturþemu þína — %s diff --git a/app/src/main/res/values-it/strings.xml b/app/src/main/res/values-it/strings.xml index b743f750df8..459bab3d3ee 100644 --- a/app/src/main/res/values-it/strings.xml +++ b/app/src/main/res/values-it/strings.xml @@ -619,7 +619,6 @@ Attiva la selezione del testo nella descrizione È possibile selezionare il testo all\'interno della descrizione. In modalità selezione la pagina potrebbe sfarfallare e i collegamenti potrebbero non essere cliccabili. Visita il sito - %s fornisce questa motivazione: Account chiuso Il recupero veloce dei feed non fornisce ulteriori informazioni al riguardo. L\'account dell\'autore è stato chiuso. diff --git a/app/src/main/res/values-ja/strings.xml b/app/src/main/res/values-ja/strings.xml index 9e8ec1c8836..3274062b571 100644 --- a/app/src/main/res/values-ja/strings.xml +++ b/app/src/main/res/values-ja/strings.xml @@ -612,7 +612,6 @@ オフ オン タブレットモード - %s がこの理由を提示: 表示しない 低品質 (小) 高品質 (大) diff --git a/app/src/main/res/values-ka/strings.xml b/app/src/main/res/values-ka/strings.xml index 45804fcfa72..b274433442d 100644 --- a/app/src/main/res/values-ka/strings.xml +++ b/app/src/main/res/values-ka/strings.xml @@ -545,7 +545,6 @@ ეს ხელმიუწვდომელია თქვენი ქვეყნიდან. ეს მასალა პირადულია, ამიტომაც NewPipe-ს მისი არც მთლიანად და არც თანდათანობით ჩამოწერა არ შეუძლია. ანგარიში შეწყვეტილია - %s იძლევა ამ მიზეზს: ეს მასალა ხელმისაწვდომია მხოლოდ გადამხდელებისთვის, ამიტომაც NewPipe-ს მისი არც მთლიანად და არც თანდათანობით ჩამოწერა არ შეუძლია. გამორჩეული რადიო diff --git a/app/src/main/res/values-ko/strings.xml b/app/src/main/res/values-ko/strings.xml index 016be87434e..6a7e463a112 100644 --- a/app/src/main/res/values-ko/strings.xml +++ b/app/src/main/res/values-ko/strings.xml @@ -645,7 +645,6 @@ 챕터 최근 계정이 해지됨 - %s은(는) 다음과 같은 이유를 제공: 이것은 적어도 귀하의 국가에서 SoundCloud Go+ 트랙이므로 NewPipe에서 스트리밍하거나 다운로드할 수 없습니다. 자동 (장치 테마) 고정된 댓글 diff --git a/app/src/main/res/values-lt/strings.xml b/app/src/main/res/values-lt/strings.xml index 3324b423c7d..91c8005cedf 100644 --- a/app/src/main/res/values-lt/strings.xml +++ b/app/src/main/res/values-lt/strings.xml @@ -623,7 +623,6 @@ Įgalinti teksto pasirinkimą apraše Neleisti pasirinkti teksto apraše Dabar apraše galite pasirinkti tekstą aprašyme. Atminkite, kad puslapis gali mirgėti, o nuorodos gali būti nespustelėjamos, kai veikia pasirinkimo režimas. - %s pateikia šią priežastį: Paskyra anuliuota Greito srauto režimas nesuteikia daugiau informacijos apie tai. Autoriaus paskyra anuliuota. diff --git a/app/src/main/res/values-lv/strings.xml b/app/src/main/res/values-lv/strings.xml index 13e163f7271..c769392cf90 100644 --- a/app/src/main/res/values-lv/strings.xml +++ b/app/src/main/res/values-lv/strings.xml @@ -631,7 +631,6 @@ \nNewPipe turpmāk nevarēs ielādēt šo plūsmu. \nVai vēlaties atteikties no šī kanāla abonēšanas\? Ātrās straumes režīms nesniedz vairāk informācijas par šo. - %s dod šādu pamatojumu: Izslēgt teksta atlasīšanu video aprakstā Iekšeji Autors piekrīt diff --git a/app/src/main/res/values-mk/strings.xml b/app/src/main/res/values-mk/strings.xml index 8b493ba0890..3a8fa2f072f 100644 --- a/app/src/main/res/values-mk/strings.xml +++ b/app/src/main/res/values-mk/strings.xml @@ -431,7 +431,6 @@ Неуспешно вчитување на новинска лента за „%s“. Прикажи / скриј стримови Оваа содржина е приватна, така што не може да биде емитувана или преземена од страна на NewPipe. - %s ја посочува следната причина: Истакнато Радио Автоматски (режим на уредот) diff --git a/app/src/main/res/values-ml/strings.xml b/app/src/main/res/values-ml/strings.xml index adba8089156..5a449025e08 100644 --- a/app/src/main/res/values-ml/strings.xml +++ b/app/src/main/res/values-ml/strings.xml @@ -613,7 +613,6 @@ ടാഗുക്കൾ വിഭാഗം താക്കൾക് ഇപ്പോൾ ഡിസ്ക്രിപ്ഷൻ ബോക്സിലെ ടെക്സ്റ്റ്‌ തിരഞ്ഞെടുക്കാൻ സാധിക്കും. ശ്രെദ്ധിക്കുക സെലെക്ഷൻ മോഡിൽ പേജ് ചിലപ്പോൾ മിന്നുകയും ലിങ്കുകൾ ക്ലിക്ക് ചെയ്യാനാകാതെയും വന്നേക്കാം. - ഇതിന്റെ കാരണം %s നൽകും: അക്കൗണ്ട് ഇല്ലാതായിരിക്കുന്നു ഫാസ്റ്റ് ഫീഡ് മോഡ് കൂടുതൽ വിവരങ്ങൾ നൽകില്ല. സൃഷ്ടാവിന്റെ അക്കൗണ്ട് ഇല്ലാതായിരിക്കുന്നു. diff --git a/app/src/main/res/values-nb-rNO/strings.xml b/app/src/main/res/values-nb-rNO/strings.xml index 027e6fe3987..d5edc2060a8 100644 --- a/app/src/main/res/values-nb-rNO/strings.xml +++ b/app/src/main/res/values-nb-rNO/strings.xml @@ -600,7 +600,6 @@ \nØnsker du å oppheve ditt abonnement på denne kanalen\? Skru av merking av tekst i beskrivelsen Skru på merking av tekst i beskrivelsen - %s oppgav denne grunnen: Konto terminert Kunne ikke laste inn informasjonskanal for «%s». Kunne ikke laste inn informasjonskanal diff --git a/app/src/main/res/values-nl/strings.xml b/app/src/main/res/values-nl/strings.xml index 75822036b05..9f99e3a705d 100644 --- a/app/src/main/res/values-nl/strings.xml +++ b/app/src/main/res/values-nl/strings.xml @@ -612,7 +612,6 @@ Aan Tablet-modus Website openen - %s geeft de volgende reden: Account getermineerd De snelle feed mode levert hierover niet meer informatie. De account van de auteur is getermineerd. diff --git a/app/src/main/res/values-nqo/strings.xml b/app/src/main/res/values-nqo/strings.xml index 73919330287..caf8509e3a7 100644 --- a/app/src/main/res/values-nqo/strings.xml +++ b/app/src/main/res/values-nqo/strings.xml @@ -627,7 +627,6 @@ ߞߐߕߐ߯ ߡߊߡߙߊߟߊ߲߫ ߛߌ߫ ߡߊ߫ ߛߐ߬ߘߐ߲߬ ߞߋߥߊߟߌ ߣߌ߲߬ ߞߊ߲ߡߊ߬. \nߘߌ߬ߢߍ߬ ߦߋ߫ ߞߐߕߐ߯ ߡߊߡߙߊߟߊ߲ ߘߏ߫ ߡߊߞߍ߫ ߡߍ߲ ߣߌ߫ ߡߙߊ߬ߘߐ߬ߦߊ ߟߊߛߐ߬ߘߐ߲ ߡߎ߬ߙߊ߲߬ߞߊ߲ߞߋ ߘߌ߫ ߓߍ߲߬ ߦߋߡߍ߲ߕߊ ߘߌ߫ ߡߊߛߐ߬ߘߐ߲߬ YouTube Music Premium ߛߌ߲߬ߝߏ߲ ߠߎ߬ ߟߋ߬ ߘߐߙߐ߲߫ ߓߟߏ߫߸ ߏ߬ ߘߐ߫ ߊ߬ ߕߍ߫ ߛߋ߫ ߘߐߛߊߙߌ߫ ߟߊ߫ ߥߟߊ߫ ߞߵߊ߬ ߟߊߖߌ߰ ߣߌߎߔߌߔ ߓߟߏ. - %s ߦߋ߫ ߞߎ߲߭ ߣߌ߲߬ ߠߋ߬ ߝߐ߫ ߟߊ߫: ߛߊ߲ߞߊߥߟߌ ߥߎߢߊ߲ߓߍ߲ ߖߘߍ߬ߢߍ߫ (ߕߙߏߞߏ߫ ߛߊߛߊ) diff --git a/app/src/main/res/values-or/strings.xml b/app/src/main/res/values-or/strings.xml index 519c8aa22d3..81184d52672 100644 --- a/app/src/main/res/values-or/strings.xml +++ b/app/src/main/res/values-or/strings.xml @@ -486,7 +486,6 @@ ସଦସ୍ୟତା ଚୟନ କରନ୍ତୁ କୌଣସି ସଦସ୍ୟତା ଚୟନ ହୋଇନାହିଁ ଦ୍ରୁତ ମୋଡ୍ ସକ୍ଷମ କରନ୍ତୁ - %s ଏହି କାରଣ ପ୍ରଦାନ କରେ: ଚ୍ୟାନେଲର ଅବତାର ଥମ୍ୱନେଲ୍ ବୈଶିଷ୍ଟ୍ୟ ରେଡିଓ diff --git a/app/src/main/res/values-pa/strings.xml b/app/src/main/res/values-pa/strings.xml index 93ea7923cbc..8b5969c0c92 100644 --- a/app/src/main/res/values-pa/strings.xml +++ b/app/src/main/res/values-pa/strings.xml @@ -455,7 +455,6 @@ ਰੇਡੀਓ ਫੀਚਰਡ ਇਹ ਸਮੱਗਰੀ ਸਿਰਫ਼ ਉਹਨਾਂ ਵਰਤੋਂਕਾਰਾਂ ਲਈ ਉਪਲਬਧ ਹੈ ਜਿੰਨ੍ਹਾਂ ਨੇ ਇਸਦੇ ਲਈ ਕੀਮਤ ਦਿੱਤੀ ਹੈ, ਇਸ ਕਰਕੇ ਨਿਊ-ਪਾਈਪ ਦੁਆਰਾ ਚਲਾਈ ਜਾਂ ਡਾਊਨਲੋਡ ਨਹੀਂ ਕੀਤੀ ਜਾ ਸਕਦੀ। - %s ਇਸਦਾ ਕਾਰਨ ਪ੍ਰਦਾਨ ਕਰਦਾ ਹੈ: ਖਾਤਾ ਬੰਦ ਕੀਤਾ ਗਿਆ ਇਹ ਵੀਡੀਓ ਸਿਰਫ਼ ਯੂਟਿਊਬ ਮਿਊਜ਼ਿਕ ਦੇ ਪ੍ਰੀਮੀਅਮ ਮੈਂਬਰਾਂ ਲਈ ਉਪਲਬਧ ਹੈ, ਇਸ ਕਰਕੇ ਨਿਊ-ਪਾਈਪ ਦੁਆਰਾ ਚਲਾਈ ਜਾਂ ਡਾਊਨਲੋਡ ਨਹੀਂ ਕੀਤੀ ਜਾ ਸਕਦੀ। ਇਹ ਸਮੱਗਰੀ ਨਿੱਜੀ (ਪ੍ਰਾਈਵੇਟ) ਹੈ, ਇਸ ਕਰਕੇ ਨਿਊ-ਪਾਈਪ ਦੁਆਰਾ ਚਲਾਈ ਜਾਂ ਡਾਊਨਲੋਡ ਨਹੀਂ ਕੀਤੀ ਜਾ ਸਕਦੀ। diff --git a/app/src/main/res/values-pl/strings.xml b/app/src/main/res/values-pl/strings.xml index 0f1ea119db0..0a95609cda0 100644 --- a/app/src/main/res/values-pl/strings.xml +++ b/app/src/main/res/values-pl/strings.xml @@ -623,7 +623,6 @@ Kategoria Otwórz stronę Teraz możesz zaznaczyć tekst wewnątrz opisu. Pamiętaj, że w trybie zaznaczania strona może migotać i linki nie będą klikalne. - %s podaje ten powód: Konto zamknięte Tryb szybki dla ładowania kanału nie dostarcza więcej informacji na ten temat. Konto autora zostało zawieszone. diff --git a/app/src/main/res/values-pt-rBR/strings.xml b/app/src/main/res/values-pt-rBR/strings.xml index 839c23c2ae5..30fc565c687 100644 --- a/app/src/main/res/values-pt-rBR/strings.xml +++ b/app/src/main/res/values-pt-rBR/strings.xml @@ -619,7 +619,6 @@ Ativar seleção de texto na descrição Agora você pode selecionar o texto dentro da descrição. Note que a página pode piscar e os URL podem não ser clicáveis no modo de seleção. Abrir site - %s fornece este motivo: Conta encerrada O modo feed rápido não fornece mais informações sobre isso. A conta do autor foi encerrada. diff --git a/app/src/main/res/values-pt-rPT/strings.xml b/app/src/main/res/values-pt-rPT/strings.xml index 3c1fe989b16..6783327ece4 100644 --- a/app/src/main/res/values-pt-rPT/strings.xml +++ b/app/src/main/res/values-pt-rPT/strings.xml @@ -623,7 +623,6 @@ Desativar seleção de texto na descrição Ativar seleção de texto na descrição Agora pode selecionar o texto na descrição. Note que a página pode cintilar e as ligações podem não ser clicáveis enquanto estiver no modo de seleção. - %s fornece este motivo: Conta encerrada O modo de feed rápido não fornece mais informações sobre isto. A conta do autor foi encerrada. diff --git a/app/src/main/res/values-pt/strings.xml b/app/src/main/res/values-pt/strings.xml index ef14944e73b..d4b35fa5541 100644 --- a/app/src/main/res/values-pt/strings.xml +++ b/app/src/main/res/values-pt/strings.xml @@ -605,7 +605,6 @@ Desativar túnel multimédia Sempre que descarregar um ficheiro, terá que indicar o local para o guardar Ainda não definiu uma pasta para as descargas. Escolha agora a pasta a utilizar - %s fornece este motivo: Conta encerrada O modo de fonte rápida não fornece mais informações sobre isto. A conta do autor foi encerrada. diff --git a/app/src/main/res/values-ro/strings.xml b/app/src/main/res/values-ro/strings.xml index 0a7711d15d2..17106ed45bd 100644 --- a/app/src/main/res/values-ro/strings.xml +++ b/app/src/main/res/values-ro/strings.xml @@ -624,7 +624,6 @@ Dezactivați selectarea textului în descriere Activați selectarea textului în descriere Acum puteți selecta text în interiorul descrierii. Rețineți că este posibil ca pagina să pâlpâie, iar linkurile să nu poată fi accesate în modul de selecție. - %s oferă acest motiv: Contul a fost închis Modul rapid nu furnizează mai multe informații în acest sens. Contul autorului a fost închis. diff --git a/app/src/main/res/values-ru/strings.xml b/app/src/main/res/values-ru/strings.xml index 96d28290b98..4e7428b3c15 100644 --- a/app/src/main/res/values-ru/strings.xml +++ b/app/src/main/res/values-ru/strings.xml @@ -633,7 +633,6 @@ Не удалось загрузить подписку \'%s\'. Ошибка загрузки подписки Открыть веб-сайт - %s указывает следующую причину: Аккаунт отключён Начиная с Android 10 поддерживается только «Storage Access Framework» Спрашивать, куда сохранять каждую загрузку diff --git a/app/src/main/res/values-ryu/strings.xml b/app/src/main/res/values-ryu/strings.xml index 9041fc46272..e9baa11dac6 100644 --- a/app/src/main/res/values-ryu/strings.xml +++ b/app/src/main/res/values-ryu/strings.xml @@ -622,7 +622,6 @@ オフ オン タブレットモード - %sやしがくぬりゆうていじ: ひょうじさん ていふぃんしち(しょう) かんふぃんしち(だい) diff --git a/app/src/main/res/values-sat/strings.xml b/app/src/main/res/values-sat/strings.xml index 6e6615a84b9..717283e8350 100644 --- a/app/src/main/res/values-sat/strings.xml +++ b/app/src/main/res/values-sat/strings.xml @@ -331,7 +331,6 @@ ᱪᱮᱯᱴᱟᱨᱥ ᱞᱟᱹᱠᱛᱤ ᱠᱟᱱᱟ ᱟᱢ ᱢᱤᱫ ᱯᱷᱤᱞ ᱢᱟᱱᱮᱡᱚᱨ ᱤᱱᱥᱴᱚᱞ ᱢᱮ ᱟᱨᱵᱟᱝ ᱰᱟᱩᱱᱞᱚᱰ ᱥᱤᱴᱤᱝ ᱨᱮ ᱵᱚᱫᱚᱞ ᱦᱚᱪᱚ ᱞᱟᱹᱜᱤᱫ ᱯᱨᱚᱵᱷᱟᱣ ᱢᱮ\" ᱱᱚᱶᱟ ᱵᱷᱤᱰᱤᱭᱳ ᱫᱚ ᱭᱩᱴᱭᱩᱵᱽ ᱢᱤᱣᱡᱤᱠ ᱯᱨᱤᱢᱤᱭᱟᱢ ᱥᱮᱞᱮᱫᱤᱭᱟᱹ ᱠᱚ ᱞᱟᱹᱜᱤᱫ ᱜᱮ ᱧᱟᱢᱚᱜᱼᱟ, ᱚᱱᱟᱛᱮ ᱱᱚᱶᱟ ᱫᱚ ᱱᱤᱭᱩ ᱯᱟᱭᱤᱯ ᱦᱚᱛᱮᱛᱮ ᱵᱟᱝ ᱥᱴᱨᱤᱢ ᱟᱨ ᱵᱟᱝ ᱰᱟᱩᱱᱞᱳᱰ ᱦᱩᱭ ᱫᱟᱲᱮᱭᱟᱜᱼᱟ ᱾ - %s ᱫᱚ ᱱᱚᱶᱟ ᱞᱟᱹᱠᱛᱤ ᱠᱟᱱᱟ: ᱚᱴᱚᱢᱟᱴᱤᱠ (ᱰᱤᱵᱟᱤᱥ ᱛᱷᱮᱢ) ᱟᱢᱟᱜ ᱯᱩᱭᱞᱩ ᱧᱤᱫᱟᱹ ᱛᱷᱤᱢ ᱵᱟᱪᱷᱟᱣ ᱢᱮ ⁇ %s ᱟᱢ ᱞᱟᱛᱟᱨ ᱨᱮ ᱟᱢᱟᱜ ᱧᱤᱫᱟᱹ ᱪᱮᱛᱟᱱ ᱵᱟᱪᱷᱟᱣ ᱫᱟᱲᱮᱭᱟᱜ ᱟ diff --git a/app/src/main/res/values-sc/strings.xml b/app/src/main/res/values-sc/strings.xml index cb51c3f4dc0..ac694bba997 100644 --- a/app/src/main/res/values-sc/strings.xml +++ b/app/src/main/res/values-sc/strings.xml @@ -610,7 +610,6 @@ Como podes ischertare su testu in intro de sa descritzione. Ammenta·ti chi sa pàgina diat pòdere trèmere e sos ligàmenes si diant pòdere no abèrrere cando ses in modalidade de ischerta. Incumintzende dae Android 10 petzi sa \'Storage Access Framework\' (Istrutura de Atzessu a s\'Archiviatzione) est suportada Aberi su situ web - %s frunit custa resone: Contu serradu Su recùperu lestru de sos flussos non frunit àteras informatziones in subra de custu. Su contu de s\'autore l\'ant serradu. diff --git a/app/src/main/res/values-sk/strings.xml b/app/src/main/res/values-sk/strings.xml index c8f2d974451..f725965e215 100644 --- a/app/src/main/res/values-sk/strings.xml +++ b/app/src/main/res/values-sk/strings.xml @@ -618,7 +618,6 @@ Povolenie výberu textu v popise Teraz môžete vybrať text vo vnútri popisu. Upozorňujeme, že stránka môže blikať a odkazy nemusia byť klikateľné, keď je v režime výberu. Otvoriť webstránku - %s uvádza tento dôvod: Účet bol zrušený Tento rýchly režim neposkytuje viac informácií. Účet autora bol zrušený. diff --git a/app/src/main/res/values-so/strings.xml b/app/src/main/res/values-so/strings.xml index 772e03b4150..860a607f5d9 100644 --- a/app/src/main/res/values-so/strings.xml +++ b/app/src/main/res/values-so/strings.xml @@ -608,7 +608,6 @@ Xidh caalamadinta qoraalka Fur caalamadinta qoraalka Hadda waad dooran kartaa qoraalka ku dhexjira faahfaahinta. Ogow markaad caalamdinayso qoraalka boggu wuu boodboodi karaa tixraacyadana waxay noqon karaan kuwo aan lagu dhufan karin. - %s wuxuu sheegayaa sababtan: Akoonka waa lajoojiyay Nidaamka dagdaga ah faahfaahin dheeraad ah uma hayo shaygan. Akoonka soosaaraha waa la joojiyay. diff --git a/app/src/main/res/values-sq/strings.xml b/app/src/main/res/values-sq/strings.xml index 9aac66de7a5..4b9c2ac3664 100644 --- a/app/src/main/res/values-sq/strings.xml +++ b/app/src/main/res/values-sq/strings.xml @@ -598,7 +598,6 @@ Zgjidhni temën tuaj të preferuar të natës - %s Automatike (tema e pajisjes) Radio - %s e jep këtë arsye: Llogaria është mbyllur Kjo përmbajtje është private, kështu që nuk mund të luhet apo shkarkohet nga NewPipe. Kjo përmbajtje nuk është e disponueshme në shtetin tuaj. diff --git a/app/src/main/res/values-sr/strings.xml b/app/src/main/res/values-sr/strings.xml index 3c82e5612ac..722ce6855b5 100644 --- a/app/src/main/res/values-sr/strings.xml +++ b/app/src/main/res/values-sr/strings.xml @@ -619,7 +619,6 @@ Омогући бирање текста унутар описа Онемогући бирање текста унутар описа Сада можете изабрати текст унутар описа. Имајте на уму да страница може треперети и да се на линкове можда неће моћи кликнути док сте у режиму избора. - %s даје овај разлог: Налог укинут Режим брзог фида не пружа више информација о овоме. Налог аутора је укинут. diff --git a/app/src/main/res/values-sv/strings.xml b/app/src/main/res/values-sv/strings.xml index 8aab4a67f0e..f3703ea87a3 100644 --- a/app/src/main/res/values-sv/strings.xml +++ b/app/src/main/res/values-sv/strings.xml @@ -586,7 +586,6 @@ Hämtningen har startat Radio Detta innehåll är endast tillgängligt för användare som har betalat för det, så det kan inte strömmas eller hämtas av NewPipe. - %s anger detta skäl: Kontot avslutat Denna video är endast tillgänglig för YouTube Music Premium-medlemmar, så den kan inte strömmas eller hämtas av NewPipe. Detta innehåll är privat, så det kan inte strömmas eller hämtas av NewPipe. diff --git a/app/src/main/res/values-ta/strings.xml b/app/src/main/res/values-ta/strings.xml index 7221ab74da5..f1d388393c7 100644 --- a/app/src/main/res/values-ta/strings.xml +++ b/app/src/main/res/values-ta/strings.xml @@ -428,7 +428,6 @@ பதிவிறக்க வரிசையை கட்டுப்படுத்துங்கள் ஒரு பதிவிறக்கம் ஒரே நேரத்தில் இயங்கும் உங்கள் சாதனத்தில் எந்த பயன்பாடும் இதைத் திறக்க முடியாது - %s இந்த காரணத்தை வழங்குகிறது: துணை சேனல் அவதாரங்கள் அவதாரங்கள் எக்சோப்ளேயர் இயல்புநிலை diff --git a/app/src/main/res/values-tr/strings.xml b/app/src/main/res/values-tr/strings.xml index 9a93d817734..c1d36422640 100644 --- a/app/src/main/res/values-tr/strings.xml +++ b/app/src/main/res/values-tr/strings.xml @@ -608,7 +608,6 @@ Açıklamadaki metni seçmeyi etkinleştir Artık, açıklamadaki metni seçebilirsiniz. Seçim kipindeyken sayfanın titreyebileceğini ve bağlantıların tıklanamayacağını unutmayın. Web sitesini aç - %s şu nedeni sağlıyor: Hesap sonlandırıldı Hızlı besleme kipi bununla ilgili daha çok bilgi sağlamıyor. Yazarın hesabı sonlandırılmış. diff --git a/app/src/main/res/values-uk/strings.xml b/app/src/main/res/values-uk/strings.xml index d7917db648e..c0bc903a055 100644 --- a/app/src/main/res/values-uk/strings.xml +++ b/app/src/main/res/values-uk/strings.xml @@ -624,7 +624,6 @@ Заборонити виділення тексту в описі Дозволити виділяти текст в описі Тепер можна виділяти текст в описі. Зауважте, що сторінка може мигати і посилання можуть не працювати в режимі виділення. - %s подає таку причину: Неможливо завантажити стрічку для «%s». Помилка завантаження стрічки Обліковий запис автора припинено. diff --git a/app/src/main/res/values-vi/strings.xml b/app/src/main/res/values-vi/strings.xml index e8f4ec3f960..d145991bc4c 100644 --- a/app/src/main/res/values-vi/strings.xml +++ b/app/src/main/res/values-vi/strings.xml @@ -602,7 +602,6 @@ Tắt chọn văn bản trong mô tả Bật chọn văn bản trong mô tả Bây giờ bạn có thể chọn văn bản trong mô tả. Lưu ý rằng trang có thể nhấp nháy và các liên kết có thể không nhấn vào được trong khi ở chế độ chọn. - %s cung cấp lý do này: Tài khoản đã bị chấm dứt Chế độ nạp nhanh không cung cấp thêm thông tin về điều này. Tài khoản của tác giả đã bị chấm dứt. diff --git a/app/src/main/res/values-zh-rCN/strings.xml b/app/src/main/res/values-zh-rCN/strings.xml index cfd2030c66e..c6e1538ece5 100644 --- a/app/src/main/res/values-zh-rCN/strings.xml +++ b/app/src/main/res/values-zh-rCN/strings.xml @@ -599,7 +599,6 @@ 启用简介中的文本选择功能 你现在可以选择简介中的文本,注意,在选择模式下,页面可能会闪烁,链接可能无法点击。 打开网站 - %s 提供这个原因: 账号被终止 快速 Feed 模式不提供关于这个的更多信息。 作者账号已被终止。 diff --git a/app/src/main/res/values-zh-rHK/strings.xml b/app/src/main/res/values-zh-rHK/strings.xml index 1f258c1db4b..24f457c2595 100644 --- a/app/src/main/res/values-zh-rHK/strings.xml +++ b/app/src/main/res/values-zh-rHK/strings.xml @@ -486,7 +486,6 @@ NewPipe 仲未支援到呢樣。 \n \n希望未來會喺日後嘅版本支援啦。 - %s 話理由如下: 搵唔到合適嘅檔案總管進行呢個動作。 \n請安裝一個檔案管理程式,又或者試下喺下載設定度停用「%s」 搵唔到合適嘅檔案總管進行呢個動作。 diff --git a/app/src/main/res/values-zh-rTW/strings.xml b/app/src/main/res/values-zh-rTW/strings.xml index 4e1fbd18edc..22dd24a3308 100644 --- a/app/src/main/res/values-zh-rTW/strings.xml +++ b/app/src/main/res/values-zh-rTW/strings.xml @@ -599,7 +599,6 @@ 啟用選取描述中的文字 您現在可以選取描述中的文字了。請注意,在選取模式下,頁面可能會閃爍,連結也可能無法點擊。 開啟網站 - %s 提供了這個理由: 帳號已終止 快速 feed 模式不會提供更多資訊。 作者的帳號已被終止。 diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index a54ddb9eedf..fc111e15ae9 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -757,7 +757,7 @@ This content is private, so it cannot be streamed or downloaded by NewPipe. This video is available only to YouTube Music Premium members, so it cannot be streamed or downloaded by NewPipe. Account terminated - %s provides this reason: + Account terminated\n\n%1$s provides this reason: %2$s This content is only available to users who have paid, so it cannot be streamed or downloaded by NewPipe. Featured Radio @@ -877,7 +877,9 @@ Trending movies and shows Trending music Entry deleted - HTTP error 403 occurred while playing, likely caused by an IP ban or streaming URL deobfuscation issues - YouTube refused to provide data, asking for a login.\n\nYour IP might have been temporarily banned by YouTube, you can wait some time or switch to a different IP (for example by turning on/off a VPN, or by switching from WiFi to mobile data). + HTTP error 403 received from server while playing, likely caused by an IP ban or by streaming URL expiration + HTTP error %1$s received from server while playing + HTTP error 403 received from server while playing, likely caused by an IP ban or streaming URL deobfuscation issues + %1$s refused to provide data, asking for a login to confirm the requester is not a bot.\n\nYour IP might have been temporarily banned by %1$s, you can wait some time or switch to a different IP (for example by turning on/off a VPN, or by switching from WiFi to mobile data). This content is not available for the currently selected content country.\n\nChange your selection from \"Settings > Content > Default content country\". From 989c0cfd284351c71bf1af314a7af4cd2741a901 Mon Sep 17 00:00:00 2001 From: Stypox Date: Sat, 30 Aug 2025 14:39:23 +0200 Subject: [PATCH 5/7] Fix REPORT in snackbar not opening ErrorActivity if MainActivity not shown Bug caused by https://github.com/TeamNewPipe/NewPipe/pull/11789 --- app/src/main/java/org/schabi/newpipe/error/ErrorUtil.kt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/src/main/java/org/schabi/newpipe/error/ErrorUtil.kt b/app/src/main/java/org/schabi/newpipe/error/ErrorUtil.kt index 520d02b3be4..b358a5fd273 100644 --- a/app/src/main/java/org/schabi/newpipe/error/ErrorUtil.kt +++ b/app/src/main/java/org/schabi/newpipe/error/ErrorUtil.kt @@ -159,7 +159,7 @@ class ErrorUtil { Snackbar.make(rootView, errorInfo.getMessage(context), Snackbar.LENGTH_LONG) .setActionTextColor(Color.YELLOW) .setAction(context.getString(R.string.error_snackbar_action).uppercase()) { - openActivity(context, errorInfo) + context.startActivity(getErrorActivityIntent(context, errorInfo)) }.show() } } From 204df4c45a4a02e37428ce67974896811ccd7d04 Mon Sep 17 00:00:00 2001 From: Stypox Date: Sat, 30 Aug 2025 14:58:08 +0200 Subject: [PATCH 6/7] Fix test --- .../schabi/newpipe/error/ErrorInfoTest.java | 20 +++++++++++++++++-- 1 file changed, 18 insertions(+), 2 deletions(-) diff --git a/app/src/androidTest/java/org/schabi/newpipe/error/ErrorInfoTest.java b/app/src/androidTest/java/org/schabi/newpipe/error/ErrorInfoTest.java index 891824a5542..892d1df0f57 100644 --- a/app/src/androidTest/java/org/schabi/newpipe/error/ErrorInfoTest.java +++ b/app/src/androidTest/java/org/schabi/newpipe/error/ErrorInfoTest.java @@ -12,6 +12,7 @@ import org.schabi.newpipe.extractor.exceptions.ParsingException; import java.util.Arrays; +import java.util.Objects; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertTrue; @@ -23,8 +24,23 @@ @LargeTest public class ErrorInfoTest { + /** + * @param errorInfo the error info to access + * @return the private field errorInfo.message.stringRes using reflection + */ + private int getMessageFromErrorInfo(final ErrorInfo errorInfo) + throws NoSuchFieldException, IllegalAccessException { + final var message = ErrorInfo.class.getDeclaredField("message"); + message.setAccessible(true); + final var messageValue = (ErrorInfo.Companion.ErrorMessage) message.get(errorInfo); + + final var stringRes = ErrorInfo.Companion.ErrorMessage.class.getDeclaredField("stringRes"); + stringRes.setAccessible(true); + return (int) Objects.requireNonNull(stringRes.get(messageValue)); + } + @Test - public void errorInfoTestParcelable() { + public void errorInfoTestParcelable() throws NoSuchFieldException, IllegalAccessException { final ErrorInfo info = new ErrorInfo(new ParsingException("Hello"), UserAction.USER_REPORT, "request", ServiceList.YouTube.getServiceId()); // Obtain a Parcel object and write the parcelable object to it: @@ -39,7 +55,7 @@ public void errorInfoTestParcelable() { assertEquals(ServiceList.YouTube.getServiceInfo().getName(), infoFromParcel.getServiceName()); assertEquals("request", infoFromParcel.getRequest()); - assertEquals(R.string.parsing_error, infoFromParcel.getMessageStringId()); + assertEquals(R.string.parsing_error, getMessageFromErrorInfo(infoFromParcel)); parcel.recycle(); } From 79980e20781dde95478012894c366ae25739c80b Mon Sep 17 00:00:00 2001 From: Stypox Date: Thu, 4 Sep 2025 13:17:45 +0200 Subject: [PATCH 7/7] Address PR reviews --- app/src/main/java/org/schabi/newpipe/error/UserAction.java | 2 +- app/src/main/res/values/strings.xml | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/app/src/main/java/org/schabi/newpipe/error/UserAction.java b/app/src/main/java/org/schabi/newpipe/error/UserAction.java index 64829523a8f..d3af9d32e1a 100644 --- a/app/src/main/java/org/schabi/newpipe/error/UserAction.java +++ b/app/src/main/java/org/schabi/newpipe/error/UserAction.java @@ -35,7 +35,7 @@ public enum UserAction { OPEN_INFO_ITEM_DIALOG("open info item dialog"), GETTING_MAIN_SCREEN_TAB("getting main screen tab"), PLAY_ON_POPUP("play on popup"), - SUBSCRIPTIONS("loading subscriptions"),; + SUBSCRIPTIONS("loading subscriptions"); private final String message; diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index fc111e15ae9..147c88938a9 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -877,7 +877,7 @@ Trending movies and shows Trending music Entry deleted - HTTP error 403 received from server while playing, likely caused by an IP ban or by streaming URL expiration + HTTP error 403 received from server while playing, likely caused by streaming URL expiration or an IP ban HTTP error %1$s received from server while playing HTTP error 403 received from server while playing, likely caused by an IP ban or streaming URL deobfuscation issues %1$s refused to provide data, asking for a login to confirm the requester is not a bot.\n\nYour IP might have been temporarily banned by %1$s, you can wait some time or switch to a different IP (for example by turning on/off a VPN, or by switching from WiFi to mobile data).