diff --git a/app/build.gradle.kts b/app/build.gradle.kts index 48a28e89be..f8b84772f5 100644 --- a/app/build.gradle.kts +++ b/app/build.gradle.kts @@ -173,11 +173,7 @@ dependencies { implementation("com.google.android.material:material:1.12.0") implementation("androidx.constraintlayout:constraintlayout:2.1.4") implementation("androidx.swiperefreshlayout:swiperefreshlayout:1.1.0") - - // Glide Module - ksp("com.github.bumptech.glide:ksp:4.16.0") - implementation("com.github.bumptech.glide:glide:4.16.0") - implementation("com.github.bumptech.glide:okhttp3-integration:4.16.0") + implementation("io.coil-kt:coil:2.7.0") // Coil Image Loading // For KSP -> Official Annotation Processors are Not Yet Supported for KSP ksp("dev.zacsweers.autoservice:auto-service-ksp:1.2.0") diff --git a/app/src/main/java/com/lagradost/cloudstream3/AcraApplication.kt b/app/src/main/java/com/lagradost/cloudstream3/AcraApplication.kt index ba94010213..ac8877ed36 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/AcraApplication.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/AcraApplication.kt @@ -22,6 +22,7 @@ import com.lagradost.cloudstream3.utils.DataStore.getKeys import com.lagradost.cloudstream3.utils.DataStore.removeKey import com.lagradost.cloudstream3.utils.DataStore.removeKeys import com.lagradost.cloudstream3.utils.DataStore.setKey +import com.lagradost.cloudstream3.utils.ImageLoader import kotlinx.coroutines.runBlocking import org.acra.ACRA import org.acra.ReportField @@ -101,6 +102,8 @@ class AcraApplication : Application() { override fun onCreate() { super.onCreate() + ImageLoader.initializeCoilImageLoader(this) + ExceptionHandler(filesDir.resolve("last_error")) { val intent = context!!.packageManager.getLaunchIntentForPackage(context!!.packageName) startActivity(Intent.makeRestartActivityTask(intent!!.component)) diff --git a/app/src/main/java/com/lagradost/cloudstream3/CommonActivity.kt b/app/src/main/java/com/lagradost/cloudstream3/CommonActivity.kt index c541dde5ba..aea23d77da 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/CommonActivity.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/CommonActivity.kt @@ -35,7 +35,7 @@ import com.lagradost.cloudstream3.actions.VideoClickActionHolder import com.lagradost.cloudstream3.databinding.ToastBinding import com.lagradost.cloudstream3.mvvm.logError import com.lagradost.cloudstream3.ui.player.PlayerEventType -import com.lagradost.cloudstream3.ui.result.UiText +import com.lagradost.cloudstream3.utils.UiText import com.lagradost.cloudstream3.ui.settings.Globals.updateTv import com.lagradost.cloudstream3.utils.AppContextUtils.isRtl import com.lagradost.cloudstream3.utils.Event diff --git a/app/src/main/java/com/lagradost/cloudstream3/MainActivity.kt b/app/src/main/java/com/lagradost/cloudstream3/MainActivity.kt index 7ea399daca..60b743711b 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/MainActivity.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/MainActivity.kt @@ -2,7 +2,6 @@ package com.lagradost.cloudstream3 import android.animation.ValueAnimator import android.annotation.SuppressLint -import android.content.ComponentName import android.content.Context import android.content.Intent import android.content.SharedPreferences @@ -10,7 +9,6 @@ import android.content.res.ColorStateList import android.content.res.Configuration import android.graphics.Rect import android.net.Uri -import android.os.Build import android.os.Bundle import android.util.AttributeSet import android.util.Log @@ -114,10 +112,9 @@ import com.lagradost.cloudstream3.ui.result.LinearListLayout import com.lagradost.cloudstream3.ui.result.ResultViewModel2 import com.lagradost.cloudstream3.ui.result.START_ACTION_RESUME_LATEST import com.lagradost.cloudstream3.ui.result.SyncViewModel -import com.lagradost.cloudstream3.ui.result.setImage -import com.lagradost.cloudstream3.ui.result.setText -import com.lagradost.cloudstream3.ui.result.setTextHtml -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.setText +import com.lagradost.cloudstream3.utils.setTextHtml +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.ui.search.SearchFragment import com.lagradost.cloudstream3.ui.search.SearchResultBuilder import com.lagradost.cloudstream3.ui.settings.Globals.EMULATOR @@ -174,6 +171,7 @@ import com.lagradost.cloudstream3.utils.UIHelper.toPx import com.lagradost.cloudstream3.utils.USER_PROVIDER_API import com.lagradost.cloudstream3.utils.USER_SELECTED_HOMEPAGE_API import com.lagradost.cloudstream3.actions.temp.fcast.FcastManager +import com.lagradost.cloudstream3.utils.ImageLoader.loadImage import com.lagradost.safefile.SafeFile import kotlinx.coroutines.sync.Mutex import kotlinx.coroutines.sync.withLock @@ -1372,7 +1370,7 @@ class MainActivity : AppCompatActivity(), ColorPickerDialogListener, BiometricCa resultviewPreviewMetaRating.setText(d.ratingText) resultviewPreviewDescription.setTextHtml(d.plotText) - resultviewPreviewPoster.setImage( + resultviewPreviewPoster.loadImage( d.posterImage ?: d.posterBackgroundImage ) @@ -1615,7 +1613,7 @@ class MainActivity : AppCompatActivity(), ColorPickerDialogListener, BiometricCa observe(homeViewModel.currentAccount) { currentAccount -> if (currentAccount != null) { - navProfilePic?.setImage( + navProfilePic?.loadImage( currentAccount.image ) navProfileRoot.isVisible = true diff --git a/app/src/main/java/com/lagradost/cloudstream3/actions/OpenInAppAction.kt b/app/src/main/java/com/lagradost/cloudstream3/actions/OpenInAppAction.kt index 8abc5e6658..cc64a6d394 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/actions/OpenInAppAction.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/actions/OpenInAppAction.kt @@ -8,14 +8,13 @@ import androidx.core.content.FileProvider import androidx.core.net.toUri import com.lagradost.cloudstream3.AcraApplication.Companion.getKey import com.lagradost.cloudstream3.AcraApplication.Companion.setKey -import com.lagradost.cloudstream3.MainActivity.Companion.activityResultLauncher import com.lagradost.cloudstream3.R import com.lagradost.cloudstream3.mvvm.logError import com.lagradost.cloudstream3.ui.result.LinkLoadingResult import com.lagradost.cloudstream3.ui.result.ResultEpisode import com.lagradost.cloudstream3.ui.result.ResultFragment -import com.lagradost.cloudstream3.ui.result.UiText -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.UiText +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.utils.AppContextUtils.isAppInstalled import com.lagradost.cloudstream3.utils.DataStoreHelper import java.io.File diff --git a/app/src/main/java/com/lagradost/cloudstream3/actions/VideoClickAction.kt b/app/src/main/java/com/lagradost/cloudstream3/actions/VideoClickAction.kt index 0d1e87a74e..7e8b1c97bb 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/actions/VideoClickAction.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/actions/VideoClickAction.kt @@ -25,7 +25,7 @@ import com.lagradost.cloudstream3.actions.temp.fcast.FcastAction import com.lagradost.cloudstream3.mvvm.logError import com.lagradost.cloudstream3.ui.result.LinkLoadingResult import com.lagradost.cloudstream3.ui.result.ResultEpisode -import com.lagradost.cloudstream3.ui.result.UiText +import com.lagradost.cloudstream3.utils.UiText import com.lagradost.cloudstream3.utils.Coroutines.ioSafe import com.lagradost.cloudstream3.utils.Coroutines.threadSafeListOf import com.lagradost.cloudstream3.utils.ExtractorLinkType diff --git a/app/src/main/java/com/lagradost/cloudstream3/actions/temp/CopyClipboardAction.kt b/app/src/main/java/com/lagradost/cloudstream3/actions/temp/CopyClipboardAction.kt index 481917e5e8..7e89d7c8c4 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/actions/temp/CopyClipboardAction.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/actions/temp/CopyClipboardAction.kt @@ -4,7 +4,7 @@ import android.content.Context import com.lagradost.cloudstream3.actions.VideoClickAction import com.lagradost.cloudstream3.ui.result.LinkLoadingResult import com.lagradost.cloudstream3.ui.result.ResultEpisode -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.utils.UIHelper.clipboardHelper class CopyClipboardAction: VideoClickAction() { diff --git a/app/src/main/java/com/lagradost/cloudstream3/actions/temp/MpvKtPackage.kt b/app/src/main/java/com/lagradost/cloudstream3/actions/temp/MpvKtPackage.kt index 6514de1748..102f0ac8bb 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/actions/temp/MpvKtPackage.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/actions/temp/MpvKtPackage.kt @@ -9,7 +9,7 @@ import com.lagradost.cloudstream3.actions.OpenInAppAction import com.lagradost.cloudstream3.actions.updateDurationAndPosition import com.lagradost.cloudstream3.ui.result.LinkLoadingResult import com.lagradost.cloudstream3.ui.result.ResultEpisode -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.utils.DataStoreHelper.getViewPos import com.lagradost.cloudstream3.utils.ExtractorLinkType diff --git a/app/src/main/java/com/lagradost/cloudstream3/actions/temp/MpvPackage.kt b/app/src/main/java/com/lagradost/cloudstream3/actions/temp/MpvPackage.kt index 382f7d89a4..68e619c92c 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/actions/temp/MpvPackage.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/actions/temp/MpvPackage.kt @@ -11,7 +11,7 @@ import com.lagradost.cloudstream3.actions.makeTempM3U8Intent import com.lagradost.cloudstream3.actions.updateDurationAndPosition import com.lagradost.cloudstream3.ui.result.LinkLoadingResult import com.lagradost.cloudstream3.ui.result.ResultEpisode -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.utils.DataStoreHelper.getViewPos import com.lagradost.cloudstream3.utils.ExtractorLinkType diff --git a/app/src/main/java/com/lagradost/cloudstream3/actions/temp/PlayInBrowserAction.kt b/app/src/main/java/com/lagradost/cloudstream3/actions/temp/PlayInBrowserAction.kt index 1558bfd6ac..7c1b68c054 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/actions/temp/PlayInBrowserAction.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/actions/temp/PlayInBrowserAction.kt @@ -7,7 +7,7 @@ import com.lagradost.cloudstream3.R import com.lagradost.cloudstream3.actions.VideoClickAction import com.lagradost.cloudstream3.ui.result.LinkLoadingResult import com.lagradost.cloudstream3.ui.result.ResultEpisode -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.utils.ExtractorLinkType class PlayInBrowserAction: VideoClickAction() { diff --git a/app/src/main/java/com/lagradost/cloudstream3/actions/temp/ViewM3U8Action.kt b/app/src/main/java/com/lagradost/cloudstream3/actions/temp/ViewM3U8Action.kt index b69562dd17..791566862e 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/actions/temp/ViewM3U8Action.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/actions/temp/ViewM3U8Action.kt @@ -7,7 +7,7 @@ import com.lagradost.cloudstream3.actions.VideoClickAction import com.lagradost.cloudstream3.actions.makeTempM3U8Intent import com.lagradost.cloudstream3.ui.result.LinkLoadingResult import com.lagradost.cloudstream3.ui.result.ResultEpisode -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.txt class ViewM3U8Action: VideoClickAction() { override val name = txt(R.string.episode_action_play_in_format, "m3u8 player") diff --git a/app/src/main/java/com/lagradost/cloudstream3/actions/temp/VlcPackage.kt b/app/src/main/java/com/lagradost/cloudstream3/actions/temp/VlcPackage.kt index 18143c0011..df4fcca812 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/actions/temp/VlcPackage.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/actions/temp/VlcPackage.kt @@ -12,7 +12,7 @@ import com.lagradost.cloudstream3.actions.makeTempM3U8Intent import com.lagradost.cloudstream3.actions.updateDurationAndPosition import com.lagradost.cloudstream3.ui.result.LinkLoadingResult import com.lagradost.cloudstream3.ui.result.ResultEpisode -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.ui.subtitles.SUBTITLE_AUTO_SELECT_KEY import com.lagradost.cloudstream3.utils.DataStoreHelper.getViewPos diff --git a/app/src/main/java/com/lagradost/cloudstream3/actions/temp/WebVideoCastPackage.kt b/app/src/main/java/com/lagradost/cloudstream3/actions/temp/WebVideoCastPackage.kt index 4f44b39696..9f7eee7b82 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/actions/temp/WebVideoCastPackage.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/actions/temp/WebVideoCastPackage.kt @@ -10,7 +10,7 @@ import com.lagradost.cloudstream3.USER_AGENT import com.lagradost.cloudstream3.actions.OpenInAppAction import com.lagradost.cloudstream3.ui.result.LinkLoadingResult import com.lagradost.cloudstream3.ui.result.ResultEpisode -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.utils.ExtractorLinkType // https://www.webvideocaster.com/integrations diff --git a/app/src/main/java/com/lagradost/cloudstream3/actions/temp/fcast/FcastAction.kt b/app/src/main/java/com/lagradost/cloudstream3/actions/temp/fcast/FcastAction.kt index 458d1dc997..e3916df01c 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/actions/temp/fcast/FcastAction.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/actions/temp/fcast/FcastAction.kt @@ -7,7 +7,7 @@ import com.lagradost.cloudstream3.USER_AGENT import com.lagradost.cloudstream3.actions.VideoClickAction import com.lagradost.cloudstream3.ui.result.LinkLoadingResult import com.lagradost.cloudstream3.ui.result.ResultEpisode -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.utils.DataStoreHelper.getViewPos import com.lagradost.cloudstream3.utils.ExtractorLink import com.lagradost.cloudstream3.utils.ExtractorLinkType diff --git a/app/src/main/java/com/lagradost/cloudstream3/plugins/PluginManager.kt b/app/src/main/java/com/lagradost/cloudstream3/plugins/PluginManager.kt index 8535592d4d..dc31b6ca17 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/plugins/PluginManager.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/plugins/PluginManager.kt @@ -33,8 +33,8 @@ import com.lagradost.cloudstream3.plugins.RepositoryManager.ONLINE_PLUGINS_FOLDE import com.lagradost.cloudstream3.plugins.RepositoryManager.PREBUILT_REPOSITORIES import com.lagradost.cloudstream3.plugins.RepositoryManager.downloadPluginToFile import com.lagradost.cloudstream3.plugins.RepositoryManager.getRepoPlugins -import com.lagradost.cloudstream3.ui.result.UiText -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.UiText +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.ui.settings.extensions.REPOSITORIES_KEY import com.lagradost.cloudstream3.ui.settings.extensions.RepositoryData import com.lagradost.cloudstream3.utils.AppContextUtils.getApiProviderLangSettings diff --git a/app/src/main/java/com/lagradost/cloudstream3/services/SubscriptionWorkManager.kt b/app/src/main/java/com/lagradost/cloudstream3/services/SubscriptionWorkManager.kt index 00c74dfff7..aef92a6ab9 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/services/SubscriptionWorkManager.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/services/SubscriptionWorkManager.kt @@ -14,7 +14,7 @@ import com.lagradost.cloudstream3.APIHolder.getApiFromNameNull import com.lagradost.cloudstream3.R import com.lagradost.cloudstream3.mvvm.logError import com.lagradost.cloudstream3.plugins.PluginManager -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.utils.AppContextUtils.createNotificationChannel import com.lagradost.cloudstream3.utils.AppContextUtils.getApiDubstatusSettings import com.lagradost.cloudstream3.utils.Coroutines.ioWork diff --git a/app/src/main/java/com/lagradost/cloudstream3/syncproviders/SyncApi.kt b/app/src/main/java/com/lagradost/cloudstream3/syncproviders/SyncApi.kt index dcb8bbead0..9d43685c83 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/syncproviders/SyncApi.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/syncproviders/SyncApi.kt @@ -3,7 +3,7 @@ package com.lagradost.cloudstream3.syncproviders import com.lagradost.cloudstream3.* import com.lagradost.cloudstream3.ui.SyncWatchType import com.lagradost.cloudstream3.ui.library.ListSorting -import com.lagradost.cloudstream3.ui.result.UiText +import com.lagradost.cloudstream3.utils.UiText import me.xdrop.fuzzywuzzy.FuzzySearch import java.util.Date diff --git a/app/src/main/java/com/lagradost/cloudstream3/syncproviders/providers/AniListApi.kt b/app/src/main/java/com/lagradost/cloudstream3/syncproviders/providers/AniListApi.kt index 6112c7dbed..68a4a9a544 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/syncproviders/providers/AniListApi.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/syncproviders/providers/AniListApi.kt @@ -15,7 +15,7 @@ import com.lagradost.cloudstream3.syncproviders.SyncAPI import com.lagradost.cloudstream3.syncproviders.SyncIdName import com.lagradost.cloudstream3.ui.SyncWatchType import com.lagradost.cloudstream3.ui.library.ListSorting -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.utils.AppContextUtils.splitQuery import com.lagradost.cloudstream3.utils.AppUtils.parseJson import com.lagradost.cloudstream3.utils.AppUtils.toJson diff --git a/app/src/main/java/com/lagradost/cloudstream3/syncproviders/providers/LocalList.kt b/app/src/main/java/com/lagradost/cloudstream3/syncproviders/providers/LocalList.kt index 0d9a4d1383..2b51f7efdf 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/syncproviders/providers/LocalList.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/syncproviders/providers/LocalList.kt @@ -7,7 +7,7 @@ import com.lagradost.cloudstream3.syncproviders.SyncAPI import com.lagradost.cloudstream3.syncproviders.SyncIdName import com.lagradost.cloudstream3.ui.WatchType import com.lagradost.cloudstream3.ui.library.ListSorting -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.ui.settings.Globals.TV import com.lagradost.cloudstream3.ui.settings.Globals.isLayout import com.lagradost.cloudstream3.utils.Coroutines.ioWork diff --git a/app/src/main/java/com/lagradost/cloudstream3/syncproviders/providers/MALApi.kt b/app/src/main/java/com/lagradost/cloudstream3/syncproviders/providers/MALApi.kt index 08c1865311..4836eca131 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/syncproviders/providers/MALApi.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/syncproviders/providers/MALApi.kt @@ -18,7 +18,7 @@ import com.lagradost.cloudstream3.syncproviders.SyncAPI import com.lagradost.cloudstream3.syncproviders.SyncIdName import com.lagradost.cloudstream3.ui.SyncWatchType import com.lagradost.cloudstream3.ui.library.ListSorting -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.utils.AppContextUtils.splitQuery import com.lagradost.cloudstream3.utils.AppUtils.parseJson import com.lagradost.cloudstream3.utils.DataStore.toKotlinObject diff --git a/app/src/main/java/com/lagradost/cloudstream3/syncproviders/providers/SimklApi.kt b/app/src/main/java/com/lagradost/cloudstream3/syncproviders/providers/SimklApi.kt index 50517f9d1a..92a181dd1c 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/syncproviders/providers/SimklApi.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/syncproviders/providers/SimklApi.kt @@ -29,7 +29,7 @@ import com.lagradost.cloudstream3.syncproviders.SyncAPI import com.lagradost.cloudstream3.syncproviders.SyncIdName import com.lagradost.cloudstream3.ui.SyncWatchType import com.lagradost.cloudstream3.ui.library.ListSorting -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.utils.AppUtils.toJson import com.lagradost.cloudstream3.utils.DataStoreHelper.toYear import okhttp3.Interceptor diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/account/AccountAdapter.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/account/AccountAdapter.kt index de0b5c058b..41ecbe7ff8 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/account/AccountAdapter.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/account/AccountAdapter.kt @@ -6,17 +6,17 @@ import androidx.core.content.ContextCompat import androidx.core.view.isVisible import androidx.recyclerview.widget.RecyclerView import androidx.viewbinding.ViewBinding +import coil.transform.RoundedCornersTransformation import com.lagradost.cloudstream3.R import com.lagradost.cloudstream3.databinding.AccountListItemAddBinding import com.lagradost.cloudstream3.databinding.AccountListItemBinding import com.lagradost.cloudstream3.databinding.AccountListItemEditBinding import com.lagradost.cloudstream3.ui.account.AccountHelper.showAccountEditDialog -import com.lagradost.cloudstream3.ui.result.setImage import com.lagradost.cloudstream3.ui.settings.Globals.EMULATOR import com.lagradost.cloudstream3.ui.settings.Globals.TV import com.lagradost.cloudstream3.ui.settings.Globals.isLayout import com.lagradost.cloudstream3.utils.DataStoreHelper -import com.lagradost.cloudstream3.utils.UIHelper.setImage +import com.lagradost.cloudstream3.utils.ImageLoader.loadImage class AccountAdapter( private val accounts: List, @@ -45,7 +45,7 @@ class AccountAdapter( val isLastUsedAccount = account.keyIndex == DataStoreHelper.selectedKeyIndex accountName.text = account.name - accountImage.setImage(account.image) + accountImage.loadImage(account.image) lockIcon.isVisible = account.lockPin != null outline.isVisible = !isTv && isLastUsedAccount @@ -87,11 +87,9 @@ class AccountAdapter( val isLastUsedAccount = account.keyIndex == DataStoreHelper.selectedKeyIndex accountName.text = account.name - accountImage.setImage( - account.image, - fadeIn = false, - radius = 10 - ) + accountImage.loadImage(account.image) { + RoundedCornersTransformation(10f) + } lockIcon.isVisible = account.lockPin != null outline.isVisible = !isTv && isLastUsedAccount diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/account/AccountHelper.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/account/AccountHelper.kt index d2aca862b9..6abf0a3481 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/account/AccountHelper.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/account/AccountHelper.kt @@ -16,6 +16,7 @@ import androidx.core.widget.doOnTextChanged import androidx.lifecycle.ViewModelProvider import androidx.recyclerview.widget.LinearLayoutManager import androidx.recyclerview.widget.RecyclerView +import coil.load import com.google.android.material.bottomsheet.BottomSheetDialog import com.lagradost.cloudstream3.AcraApplication.Companion.getActivity import com.lagradost.cloudstream3.MainActivity @@ -25,11 +26,11 @@ import com.lagradost.cloudstream3.databinding.AccountSelectLinearBinding import com.lagradost.cloudstream3.databinding.LockPinDialogBinding import com.lagradost.cloudstream3.mvvm.logError import com.lagradost.cloudstream3.mvvm.observe -import com.lagradost.cloudstream3.ui.result.setImage import com.lagradost.cloudstream3.ui.result.setLinearListLayout import com.lagradost.cloudstream3.utils.AppContextUtils.setDefaultFocus import com.lagradost.cloudstream3.utils.DataStoreHelper import com.lagradost.cloudstream3.utils.DataStoreHelper.getDefaultAccount +import com.lagradost.cloudstream3.utils.ImageLoader.loadImage import com.lagradost.cloudstream3.utils.UIHelper.dismissSafe import com.lagradost.cloudstream3.utils.UIHelper.showInputMethod @@ -90,12 +91,12 @@ object AccountHelper { } // Handle the profile picture and its interactions - binding.accountImage.setImage(account.image) + binding.accountImage.loadImage(account.image) binding.accountImage.setOnClickListener { // Roll the image forwards once currentEditAccount = currentEditAccount.copy(defaultImageIndex = (currentEditAccount.defaultImageIndex + 1) % DataStoreHelper.profileImages.size) - binding.accountImage.setImage(currentEditAccount.image) + binding.accountImage.loadImage(currentEditAccount.image) } // Handle applying changes diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/download/DownloadAdapter.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/download/DownloadAdapter.kt index d211cb87ce..a0e5cabc46 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/download/DownloadAdapter.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/download/DownloadAdapter.kt @@ -18,7 +18,7 @@ import com.lagradost.cloudstream3.ui.download.button.DownloadStatusTell import com.lagradost.cloudstream3.utils.AppContextUtils.getNameFull import com.lagradost.cloudstream3.utils.DataStoreHelper.fixVisual import com.lagradost.cloudstream3.utils.DataStoreHelper.getViewPos -import com.lagradost.cloudstream3.utils.UIHelper.setImage +import com.lagradost.cloudstream3.utils.ImageLoader.loadImage import com.lagradost.cloudstream3.utils.VideoDownloadHelper const val DOWNLOAD_ACTION_PLAY_FILE = 0 @@ -108,7 +108,7 @@ class DownloadAdapter( } downloadHeaderPoster.apply { - setImage(data.poster) + loadImage(data.poster) if (isMultiDeleteState) { setOnClickListener { toggleIsChecked(deleteCheckbox, data.id) diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/home/HomeFragment.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/home/HomeFragment.kt index 2189c9e44d..e8daa4eb49 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/home/HomeFragment.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/home/HomeFragment.kt @@ -22,7 +22,6 @@ import androidx.recyclerview.widget.RecyclerView import com.google.android.material.bottomsheet.BottomSheetBehavior import com.google.android.material.bottomsheet.BottomSheetDialog import com.google.android.material.chip.Chip -import com.lagradost.api.Log import com.lagradost.cloudstream3.* import com.lagradost.cloudstream3.APIHolder.apis import com.lagradost.cloudstream3.CommonActivity.showToast @@ -37,7 +36,7 @@ import com.lagradost.cloudstream3.mvvm.observeNullable import com.lagradost.cloudstream3.ui.APIRepository.Companion.noneApi import com.lagradost.cloudstream3.ui.APIRepository.Companion.randomApi import com.lagradost.cloudstream3.ui.account.AccountHelper.showAccountSelectLinear -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.ui.search.* import com.lagradost.cloudstream3.ui.search.SearchHelper.handleSearchClickCallback import com.lagradost.cloudstream3.ui.settings.Globals.EMULATOR @@ -58,7 +57,6 @@ import com.lagradost.cloudstream3.utils.SubtitleHelper.getFlagFromIso import com.lagradost.cloudstream3.utils.UIHelper.dismissSafe import com.lagradost.cloudstream3.utils.UIHelper.getSpanCount import com.lagradost.cloudstream3.utils.UIHelper.popupMenuNoIconsAndNoStringRes -import com.lagradost.cloudstream3.utils.UIHelper.setImage import java.util.* diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/home/HomeScrollAdapter.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/home/HomeScrollAdapter.kt index 29186e83a4..4c4dd2d84d 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/home/HomeScrollAdapter.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/home/HomeScrollAdapter.kt @@ -13,7 +13,7 @@ import com.lagradost.cloudstream3.ui.ViewHolderState import com.lagradost.cloudstream3.ui.settings.Globals.EMULATOR import com.lagradost.cloudstream3.ui.settings.Globals.TV import com.lagradost.cloudstream3.ui.settings.Globals.isLayout -import com.lagradost.cloudstream3.utils.UIHelper.setImage +import com.lagradost.cloudstream3.utils.ImageLoader.loadImage class HomeScrollAdapter( fragment: Fragment @@ -47,7 +47,7 @@ class HomeScrollAdapter( when (binding) { is HomeScrollViewBinding -> { - binding.homeScrollPreview.setImage(posterUrl) + binding.homeScrollPreview.loadImage(posterUrl) binding.homeScrollPreviewTags.apply { text = item.tags?.joinToString(" • ") ?: "" isGone = item.tags.isNullOrEmpty() @@ -57,7 +57,7 @@ class HomeScrollAdapter( } is HomeScrollViewTvBinding -> { - binding.homeScrollPreview.setImage(posterUrl) + binding.homeScrollPreview.loadImage(posterUrl) } } } diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/library/LibraryFragment.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/library/LibraryFragment.kt index 5b240693bc..8e3abf058f 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/library/LibraryFragment.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/library/LibraryFragment.kt @@ -46,7 +46,7 @@ import com.lagradost.cloudstream3.syncproviders.SyncAPI import com.lagradost.cloudstream3.syncproviders.SyncIdName import com.lagradost.cloudstream3.ui.AutofitRecyclerView import com.lagradost.cloudstream3.ui.quicksearch.QuickSearchFragment -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.ui.search.SEARCH_ACTION_LOAD import com.lagradost.cloudstream3.ui.search.SEARCH_ACTION_SHOW_METADATA import com.lagradost.cloudstream3.ui.settings.Globals.EMULATOR diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/player/FullScreenPlayer.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/player/FullScreenPlayer.kt index 70f7e36865..f974436cb8 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/player/FullScreenPlayer.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/player/FullScreenPlayer.kt @@ -53,8 +53,8 @@ import com.lagradost.cloudstream3.databinding.SubtitleOffsetBinding import com.lagradost.cloudstream3.mvvm.logError import com.lagradost.cloudstream3.ui.player.GeneratorPlayer.Companion.subsProvidersIsActive import com.lagradost.cloudstream3.ui.player.source_priority.QualityDataHelper -import com.lagradost.cloudstream3.ui.result.setText -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.setText +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.ui.settings.Globals.EMULATOR import com.lagradost.cloudstream3.ui.settings.Globals.TV import com.lagradost.cloudstream3.ui.settings.Globals.isLayout diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/player/source_priority/ProfilesAdapter.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/player/source_priority/ProfilesAdapter.kt index 45f6aa6608..886c8837b9 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/player/source_priority/ProfilesAdapter.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/player/source_priority/ProfilesAdapter.kt @@ -8,13 +8,14 @@ import android.view.ViewGroup import android.widget.ImageView import android.widget.TextView import androidx.core.content.ContextCompat +import androidx.core.graphics.drawable.toBitmap import androidx.core.view.isVisible +import androidx.palette.graphics.Palette import androidx.recyclerview.widget.RecyclerView import com.lagradost.cloudstream3.R import com.lagradost.cloudstream3.databinding.PlayerQualityProfileItemBinding -import com.lagradost.cloudstream3.ui.result.UiImage import com.lagradost.cloudstream3.utils.AppContextUtils -import com.lagradost.cloudstream3.utils.UIHelper.setImage +import com.lagradost.cloudstream3.utils.ImageLoader.loadImage class ProfilesAdapter( override val items: MutableList, @@ -81,15 +82,25 @@ class ProfilesAdapter( outline.isVisible = currentItem?.second?.id == item.id - profileBg.setImage(UiImage.Drawable(art[index % art.size]), null, false) { palette -> - val color = palette.getDarkVibrantColor( - ContextCompat.getColor( - itemView.context, - R.color.dubColorBg - ) - ) - wifiText.backgroundTintList = ColorStateList.valueOf(color) - dataText.backgroundTintList = ColorStateList.valueOf(color) + profileBg.loadImage(art[index % art.size]) { + target { drawable -> + // Convert drawable to bitmap to extract palette colors + val bitmap = drawable.toBitmap() + + Palette.from(bitmap).generate { palette -> + palette?.let { + val color = it.getDarkVibrantColor( + ContextCompat.getColor( + itemView.context, + R.color.dubColorBg + ) + ) + + wifiText.backgroundTintList = ColorStateList.valueOf(color) + dataText.backgroundTintList = ColorStateList.valueOf(color) + } + } + } } val textStyle = diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/player/source_priority/QualityDataHelper.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/player/source_priority/QualityDataHelper.kt index 3267efd73c..0922bdb5aa 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/player/source_priority/QualityDataHelper.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/player/source_priority/QualityDataHelper.kt @@ -6,8 +6,8 @@ import com.lagradost.cloudstream3.AcraApplication.Companion.removeKey import com.lagradost.cloudstream3.AcraApplication.Companion.setKey import com.lagradost.cloudstream3.R import com.lagradost.cloudstream3.mvvm.debugAssert -import com.lagradost.cloudstream3.ui.result.UiText -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.UiText +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.utils.DataStoreHelper.currentAccount import com.lagradost.cloudstream3.utils.Qualities diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/player/source_priority/QualityProfileDialog.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/player/source_priority/QualityProfileDialog.kt index 0537092c18..19e98138cb 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/player/source_priority/QualityProfileDialog.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/player/source_priority/QualityProfileDialog.kt @@ -7,7 +7,7 @@ import com.lagradost.cloudstream3.R import com.lagradost.cloudstream3.databinding.PlayerQualityProfileDialogBinding import com.lagradost.cloudstream3.ui.player.source_priority.QualityDataHelper.getProfileName import com.lagradost.cloudstream3.ui.player.source_priority.QualityDataHelper.getProfiles -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.utils.ExtractorLink import com.lagradost.cloudstream3.utils.SingleSelectionHelper.showBottomDialog import com.lagradost.cloudstream3.utils.UIHelper.dismissSafe diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/player/source_priority/SourcePriorityDialog.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/player/source_priority/SourcePriorityDialog.kt index bc6282af2c..4c74ec80f3 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/player/source_priority/SourcePriorityDialog.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/player/source_priority/SourcePriorityDialog.kt @@ -7,7 +7,7 @@ import androidx.annotation.StyleRes import androidx.appcompat.app.AlertDialog import com.lagradost.cloudstream3.R import com.lagradost.cloudstream3.databinding.PlayerSelectSourcePriorityBinding -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.utils.ExtractorLink import com.lagradost.cloudstream3.utils.Qualities import com.lagradost.cloudstream3.utils.UIHelper.dismissSafe diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/result/ActorAdaptor.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/result/ActorAdaptor.kt index 0ca326ddf8..8ffe2e04b3 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/result/ActorAdaptor.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/result/ActorAdaptor.kt @@ -10,7 +10,7 @@ import com.lagradost.cloudstream3.ActorData import com.lagradost.cloudstream3.ActorRole import com.lagradost.cloudstream3.R import com.lagradost.cloudstream3.databinding.CastItemBinding -import com.lagradost.cloudstream3.utils.UIHelper.setImage +import com.lagradost.cloudstream3.utils.ImageLoader.loadImage class ActorAdaptor( private var nextFocusUpId: Int? = null, @@ -102,7 +102,7 @@ class ActorAdaptor( } binding.apply { - actorImage.setImage(mainImg) + actorImage.loadImage(mainImg) actorName.text = actor.actor.name actor.role?.let { @@ -136,7 +136,9 @@ class ActorAdaptor( voiceActorName.isVisible = false } else { voiceActorName.text = actor.voiceActor?.name - voiceActorImageHolder.isVisible = voiceActorImage.setImage(vaImage) + if (!vaImage.isNullOrEmpty()) + voiceActorImageHolder.isVisible = true + voiceActorImage.loadImage(vaImage) } } } diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/result/EpisodeAdapter.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/result/EpisodeAdapter.kt index 2dd8e2ab4d..51acd15a44 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/result/EpisodeAdapter.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/result/EpisodeAdapter.kt @@ -23,9 +23,11 @@ import com.lagradost.cloudstream3.ui.settings.Globals.PHONE import com.lagradost.cloudstream3.ui.settings.Globals.TV import com.lagradost.cloudstream3.ui.settings.Globals.isLayout import com.lagradost.cloudstream3.utils.AppContextUtils.html -import com.lagradost.cloudstream3.utils.UIHelper.setImage +import com.lagradost.cloudstream3.utils.ImageLoader.loadImage import com.lagradost.cloudstream3.utils.UIHelper.toPx import com.lagradost.cloudstream3.utils.VideoDownloadHelper +import com.lagradost.cloudstream3.utils.setText +import com.lagradost.cloudstream3.utils.txt import java.text.DateFormat import java.text.SimpleDateFormat import java.util.Date @@ -225,7 +227,7 @@ class EpisodeAdapter( episodeProgress.isVisible = displayPos > 0L } - episodePoster.isVisible = episodePoster.setImage(card.poster) == true + episodePoster.loadImage(card.poster) if (card.rating != null) { episodeRating.text = episodeRating.context?.getString(R.string.rated_format) @@ -260,7 +262,7 @@ class EpisodeAdapter( episodePlayIcon.isVisible = false episodeUpcomingIcon.isVisible = !episodePoster.isVisible episodeDate.setText( - txt( + com.lagradost.cloudstream3.utils.txt( R.string.episode_upcoming_format, secondsToReadable( card.airDate.minus(unixTimeMS).div(1000).toInt(), diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/result/ResultFragmentPhone.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/result/ResultFragmentPhone.kt index 97bc49eaee..119bd57f00 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/result/ResultFragmentPhone.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/result/ResultFragmentPhone.kt @@ -64,6 +64,7 @@ import com.lagradost.cloudstream3.utils.AppContextUtils.openBrowser import com.lagradost.cloudstream3.utils.AppContextUtils.updateHasTrailers import com.lagradost.cloudstream3.utils.BatteryOptimizationChecker.openBatteryOptimizationSettings import com.lagradost.cloudstream3.utils.ExtractorLink +import com.lagradost.cloudstream3.utils.ImageLoader.loadImage import com.lagradost.cloudstream3.utils.SingleSelectionHelper.showBottomDialog import com.lagradost.cloudstream3.utils.SingleSelectionHelper.showBottomDialogInstant import com.lagradost.cloudstream3.utils.SingleSelectionHelper.showDialog @@ -75,8 +76,9 @@ import com.lagradost.cloudstream3.utils.UIHelper.hideKeyboard import com.lagradost.cloudstream3.utils.UIHelper.popCurrentPage import com.lagradost.cloudstream3.utils.UIHelper.populateChips import com.lagradost.cloudstream3.utils.UIHelper.popupMenuNoIconsAndNoStringRes -import com.lagradost.cloudstream3.utils.UIHelper.setImage import com.lagradost.cloudstream3.utils.VideoDownloadHelper +import com.lagradost.cloudstream3.utils.setText +import com.lagradost.cloudstream3.utils.setTextHtml open class ResultFragmentPhone : FullScreenPlayer() { private val gestureRegionsListener = @@ -449,8 +451,8 @@ open class ResultFragmentPhone : FullScreenPlayer() { } val name = (viewModel.page.value as? Resource.Success)?.value?.title - ?: txt(R.string.no_data).asStringNull(context) ?: "" - showToast(txt(message, name), Toast.LENGTH_SHORT) + ?: com.lagradost.cloudstream3.utils.txt(R.string.no_data).asStringNull(context) ?: "" + showToast(com.lagradost.cloudstream3.utils.txt(message, name), Toast.LENGTH_SHORT) } context?.let { openBatteryOptimizationSettings(it) } } @@ -465,8 +467,8 @@ open class ResultFragmentPhone : FullScreenPlayer() { } val name = (viewModel.page.value as? Resource.Success)?.value?.title - ?: txt(R.string.no_data).asStringNull(context) ?: "" - showToast(txt(message, name), Toast.LENGTH_SHORT) + ?: com.lagradost.cloudstream3.utils.txt(R.string.no_data).asStringNull(context) ?: "" + showToast(com.lagradost.cloudstream3.utils.txt(message, name), Toast.LENGTH_SHORT) } } mediaRouteButton.apply { @@ -703,8 +705,12 @@ open class ResultFragmentPhone : FullScreenPlayer() { resultCastText.setText(d.actorsText) resultNextAiring.setText(d.nextAiringEpisode) resultNextAiringTime.setText(d.nextAiringDate) - resultPoster.setImage(d.posterImage) - resultPosterBackground.setImage(d.posterBackgroundImage) + resultPoster.loadImage(d.posterImage, headers = d.posterHeaders) { + error(R.drawable.default_cover) + } + resultPosterBackground.loadImage(d.posterBackgroundImage, headers = d.posterHeaders) { + error(R.drawable.default_cover) + } var isExpanded = false resultDescription.apply { @@ -776,7 +782,7 @@ open class ResultFragmentPhone : FullScreenPlayer() { resultReloadConnectionOpenInBrowser.isVisible = data is Resource.Failure resultTitle.setOnLongClickListener { - clipboardHelper(txt(R.string.title), resultTitle.text) + clipboardHelper(com.lagradost.cloudstream3.utils.txt(R.string.title), resultTitle.text) true } } diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/result/ResultFragmentTv.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/result/ResultFragmentTv.kt index 1878f0b8f4..b92cc250c4 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/result/ResultFragmentTv.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/result/ResultFragmentTv.kt @@ -46,6 +46,7 @@ import com.lagradost.cloudstream3.utils.AppContextUtils.html import com.lagradost.cloudstream3.utils.AppContextUtils.isRtl import com.lagradost.cloudstream3.utils.AppContextUtils.loadCache import com.lagradost.cloudstream3.utils.AppContextUtils.updateHasTrailers +import com.lagradost.cloudstream3.utils.ImageLoader.loadImage import com.lagradost.cloudstream3.utils.SingleSelectionHelper.showBottomDialog import com.lagradost.cloudstream3.utils.SingleSelectionHelper.showBottomDialogInstant import com.lagradost.cloudstream3.utils.UIHelper @@ -53,7 +54,8 @@ import com.lagradost.cloudstream3.utils.UIHelper.colorFromAttribute import com.lagradost.cloudstream3.utils.UIHelper.dismissSafe import com.lagradost.cloudstream3.utils.UIHelper.hideKeyboard import com.lagradost.cloudstream3.utils.UIHelper.navigate -import com.lagradost.cloudstream3.utils.UIHelper.setImage +import com.lagradost.cloudstream3.utils.setText +import com.lagradost.cloudstream3.utils.setTextHtml class ResultFragmentTv : Fragment() { private lateinit var viewModel: ResultViewModel2 @@ -150,7 +152,9 @@ class ResultFragmentTv : Fragment() { rec?.map { it.apiName }?.distinct()?.let { apiNames -> // very dirty selection resultRecommendationsFilterSelection.isVisible = apiNames.size > 1 - resultRecommendationsFilterSelection.update(apiNames.map { txt(it) to it }) + resultRecommendationsFilterSelection.update(apiNames.map { com.lagradost.cloudstream3.utils.txt( + it + ) to it }) resultRecommendationsFilterSelection.select(apiNames.indexOf(matchAgainst)) } ?: run { resultRecommendationsFilterSelection.isVisible = false @@ -579,8 +583,12 @@ class ResultFragmentTv : Fragment() { } val name = (viewModel.page.value as? Resource.Success)?.value?.title - ?: txt(R.string.no_data).asStringNull(context) ?: "" - CommonActivity.showToast(txt(message, name), Toast.LENGTH_SHORT) + ?: com.lagradost.cloudstream3.utils.txt(R.string.no_data).asStringNull(context) ?: "" + CommonActivity.showToast( + com.lagradost.cloudstream3.utils.txt( + message, + name + ), Toast.LENGTH_SHORT) } } } @@ -622,8 +630,12 @@ class ResultFragmentTv : Fragment() { } val name = (viewModel.page.value as? Resource.Success)?.value?.title - ?: txt(R.string.no_data).asStringNull(context) ?: "" - CommonActivity.showToast(txt(message, name), Toast.LENGTH_SHORT) + ?: com.lagradost.cloudstream3.utils.txt(R.string.no_data).asStringNull(context) ?: "" + CommonActivity.showToast( + com.lagradost.cloudstream3.utils.txt( + message, + name + ), Toast.LENGTH_SHORT) } } @@ -839,7 +851,7 @@ class ResultFragmentTv : Fragment() { resultCastText.setText(d.actorsText) resultNextAiring.setText(d.nextAiringEpisode) resultNextAiringTime.setText(d.nextAiringDate) - resultPoster.setImage(d.posterImage) + resultPoster.loadImage(d.posterImage) var isExpanded = false resultDescription.apply { @@ -874,11 +886,9 @@ class ResultFragmentTv : Fragment() { //Change poster crop area to 20% from Top backgroundPoster.cropYCenterOffsetPct = 0.20F - backgroundPoster.setImage( - d.posterBackgroundImage ?: UiImage.Drawable(error), - radius = 0, - errorImageDrawable = error - ) + backgroundPoster.loadImage( + d.posterBackgroundImage + ) { error(error) } comingSoon = d.comingSoon resultTvComingSoon.isVisible = d.comingSoon diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/result/ResultViewModel2.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/result/ResultViewModel2.kt index bf3b82a910..4cd3d4da58 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/result/ResultViewModel2.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/result/ResultViewModel2.kt @@ -81,7 +81,6 @@ import com.lagradost.cloudstream3.utils.DataStoreHelper.setResultWatchState import com.lagradost.cloudstream3.utils.DataStoreHelper.setSubscribedData import com.lagradost.cloudstream3.utils.DataStoreHelper.setVideoWatchState import com.lagradost.cloudstream3.utils.DataStoreHelper.updateSubscribedData -import com.lagradost.cloudstream3.utils.UIHelper.clipboardHelper import com.lagradost.cloudstream3.utils.UIHelper.navigate import kotlinx.coroutines.* import java.util.concurrent.TimeUnit @@ -114,8 +113,8 @@ data class ResultData( val title: String, var syncData: Map, - val posterImage: UiImage?, - val posterBackgroundImage: UiImage?, + val posterImage: String?, + val posterBackgroundImage: String?, val plotText: UiText, val apiName: UiText, val ratingText: UiText?, @@ -131,6 +130,7 @@ data class ResultData( val nextAiringDate: UiText?, val nextAiringEpisode: UiText?, val plotHeaderText: UiText, + val posterHeaders: Map? = null, ) data class CheckDuplicateData( @@ -215,12 +215,9 @@ fun LoadResponse.toResultData(repo: APIRepository): ResultData { ), nextAiringDate = nextAiringDate, nextAiringEpisode = nextAiringEpisode, - posterImage = img( - posterUrl, posterHeaders - ) ?: img(R.drawable.default_cover), - posterBackgroundImage = img( - backgroundPosterUrl ?: posterUrl, posterHeaders - ) ?: img(R.drawable.default_cover), + posterImage = posterUrl ?: backgroundPosterUrl, + posterHeaders = posterHeaders, + posterBackgroundImage = backgroundPosterUrl ?: posterUrl, titleText = txt(name), url = url, tags = tags ?: emptyList(), diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/result/SelectAdaptor.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/result/SelectAdaptor.kt index 8752e275c7..ad5d89d18e 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/result/SelectAdaptor.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/result/SelectAdaptor.kt @@ -8,6 +8,8 @@ import com.google.android.material.button.MaterialButton import com.lagradost.cloudstream3.databinding.ResultSelectionBinding import com.lagradost.cloudstream3.ui.settings.Globals.TV import com.lagradost.cloudstream3.ui.settings.Globals.isLayout +import com.lagradost.cloudstream3.utils.UiText +import com.lagradost.cloudstream3.utils.setText typealias SelectData = Pair diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/search/SearchResultBuilder.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/search/SearchResultBuilder.kt index 92575e58fb..37e658bfc9 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/search/SearchResultBuilder.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/search/SearchResultBuilder.kt @@ -23,8 +23,8 @@ import com.lagradost.cloudstream3.ui.settings.Globals.isLayout import com.lagradost.cloudstream3.utils.AppContextUtils.getNameFull import com.lagradost.cloudstream3.utils.DataStoreHelper import com.lagradost.cloudstream3.utils.DataStoreHelper.fixVisual +import com.lagradost.cloudstream3.utils.ImageLoader.loadImage import com.lagradost.cloudstream3.utils.SubtitleHelper -import com.lagradost.cloudstream3.utils.UIHelper.setImage object SearchResultBuilder { private val showCache: MutableMap = mutableMapOf() @@ -120,10 +120,7 @@ object SearchResultBuilder { cardText?.text = card.name cardText?.isVisible = showTitle cardView.isVisible = true - - if (!cardView.setImage(card.posterUrl, card.posterHeaders, colorCallback = colorCallback)) { - cardView.setImageResource(R.drawable.default_cover) - } + cardView.loadImage(card.posterUrl) { error(R.drawable.default_cover) } fun click(view: View?) { clickCallback.invoke( diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/settings/AccountAdapter.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/settings/AccountAdapter.kt index d7bd69f115..ba53f96f1f 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/settings/AccountAdapter.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/settings/AccountAdapter.kt @@ -9,7 +9,7 @@ import androidx.recyclerview.widget.RecyclerView import com.lagradost.cloudstream3.R import com.lagradost.cloudstream3.databinding.AccountSingleBinding import com.lagradost.cloudstream3.syncproviders.AuthAPI -import com.lagradost.cloudstream3.utils.UIHelper.setImage +import com.lagradost.cloudstream3.utils.ImageLoader.loadImage class AccountClickCallback(val action: Int, val view: View, val card: AuthAPI.LoginInfo) @@ -43,22 +43,23 @@ class AccountAdapter( return cardList[position].accountIndex.toLong() } - class CardViewHolder(val binding: AccountSingleBinding, private val clickCallback: (AccountClickCallback) -> Unit) : - RecyclerView.ViewHolder(binding.root) { - // private val pfp: ImageView = itemView.findViewById(R.id.account_profile_picture)!! - // private val accountName: TextView = itemView.findViewById(R.id.account_name)!! + class CardViewHolder(val binding: AccountSingleBinding?, private val clickCallback: (AccountClickCallback) -> Unit) : + RecyclerView.ViewHolder(binding?.root!!) { @SuppressLint("StringFormatInvalid") fun bind(card: AuthAPI.LoginInfo) { // just in case name is null account index will show, should never happened - binding.accountName.text = card.name ?: "%s %d".format( - binding.accountName.context.getString(R.string.account), - card.accountIndex - ) - binding.accountProfilePicture.isVisible = binding.accountProfilePicture.setImage(card.profilePicture) + binding?.apply { + accountName.text = card.name ?: "%s %d".format( + binding.accountName.context.getString(R.string.account), + card.accountIndex + ) + accountProfilePicture.isVisible = true + accountProfilePicture.loadImage(card.profilePicture) - itemView.setOnClickListener { - clickCallback.invoke(AccountClickCallback(0, itemView, card)) + itemView.setOnClickListener { + clickCallback.invoke(AccountClickCallback(0, itemView, card)) + } } } } diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/settings/SettingsAccount.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/settings/SettingsAccount.kt index 15f8735fea..daeab0500d 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/settings/SettingsAccount.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/settings/SettingsAccount.kt @@ -34,10 +34,6 @@ import com.lagradost.cloudstream3.syncproviders.AccountManager.Companion.subDlAp import com.lagradost.cloudstream3.syncproviders.AuthAPI import com.lagradost.cloudstream3.syncproviders.InAppAuthAPI import com.lagradost.cloudstream3.syncproviders.OAuth2API -import com.lagradost.cloudstream3.ui.result.img -import com.lagradost.cloudstream3.ui.result.setImage -import com.lagradost.cloudstream3.ui.result.setText -import com.lagradost.cloudstream3.ui.result.txt import com.lagradost.cloudstream3.ui.settings.Globals.EMULATOR import com.lagradost.cloudstream3.ui.settings.Globals.PHONE import com.lagradost.cloudstream3.ui.settings.Globals.TV @@ -57,11 +53,13 @@ import com.lagradost.cloudstream3.utils.BiometricAuthenticator.isAuthEnabled import com.lagradost.cloudstream3.utils.BiometricAuthenticator.promptInfo import com.lagradost.cloudstream3.utils.BiometricAuthenticator.startBiometricAuthentication import com.lagradost.cloudstream3.utils.Coroutines.ioSafe +import com.lagradost.cloudstream3.utils.ImageLoader.loadImage import com.lagradost.cloudstream3.utils.SingleSelectionHelper.showBottomDialogText import com.lagradost.cloudstream3.utils.UIHelper.colorFromAttribute import com.lagradost.cloudstream3.utils.UIHelper.dismissSafe import com.lagradost.cloudstream3.utils.UIHelper.hideKeyboard -import com.lagradost.cloudstream3.utils.UIHelper.setImage +import com.lagradost.cloudstream3.utils.setText +import com.lagradost.cloudstream3.utils.txt import qrcode.QRCode class SettingsAccount : PreferenceFragmentCompat(), BiometricCallback { @@ -80,8 +78,9 @@ class SettingsAccount : PreferenceFragmentCompat(), BiometricCallback { .setView(binding.root) val dialog = builder.show() - binding.accountMainProfilePictureHolder.isVisible = - binding.accountMainProfilePicture.setImage(info.profilePicture) + binding.accountMainProfilePictureHolder.isVisible = !info.profilePicture.isNullOrEmpty() + binding.accountMainProfilePicture.loadImage(info.profilePicture) + binding.accountLogout.setOnClickListener { api.logOut() @@ -198,9 +197,7 @@ class SettingsAccount : PreferenceFragmentCompat(), BiometricCallback { pinCodeData.verificationUrl ) ) - deviceAuthQrcode.setImage( - img(qrCodeImage) - ) + deviceAuthQrcode.loadImage(qrCodeImage) } val expirationMillis = diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/settings/SettingsFragment.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/settings/SettingsFragment.kt index 339fe752d1..ef35971ce4 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/settings/SettingsFragment.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/settings/SettingsFragment.kt @@ -20,17 +20,17 @@ import com.lagradost.cloudstream3.databinding.MainSettingsBinding import com.lagradost.cloudstream3.mvvm.logError import com.lagradost.cloudstream3.syncproviders.AccountManager import com.lagradost.cloudstream3.syncproviders.AccountManager.Companion.accountManagers -import com.lagradost.cloudstream3.ui.home.HomeFragment -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.ui.home.HomeFragment.Companion.errorProfilePic +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.ui.settings.Globals.EMULATOR import com.lagradost.cloudstream3.ui.settings.Globals.PHONE import com.lagradost.cloudstream3.ui.settings.Globals.TV import com.lagradost.cloudstream3.ui.settings.Globals.isLayout import com.lagradost.cloudstream3.utils.DataStoreHelper +import com.lagradost.cloudstream3.utils.ImageLoader.loadImage import com.lagradost.cloudstream3.utils.UIHelper import com.lagradost.cloudstream3.utils.UIHelper.clipboardHelper import com.lagradost.cloudstream3.utils.UIHelper.navigate -import com.lagradost.cloudstream3.utils.UIHelper.setImage import com.lagradost.cloudstream3.utils.UIHelper.toPx import java.io.File import java.text.DateFormat @@ -184,14 +184,14 @@ class SettingsFragment : Fragment() { val login = syncApi.loginInfo() val pic = login?.profilePicture ?: continue - if (binding?.settingsProfilePic?.setImage( - pic, - errorImageDrawable = HomeFragment.errorProfilePic - ) == true - ) { - binding?.settingsProfileText?.text = login.name - return true // sync profile exists + binding?.settingsProfilePic?.let { imageView -> + imageView.loadImage(pic) { + crossfade(true) // Optional: for a fade-in animation + error(errorProfilePic) // Fallback to random error drawable + } } + return true // sync profile exists + } return false // not syncing } @@ -209,7 +209,7 @@ class SettingsFragment : Fragment() { null } - binding?.settingsProfilePic?.setImage(currentAccount?.image) + binding?.settingsProfilePic?.loadImage(currentAccount?.image) binding?.settingsProfileText?.text = currentAccount?.name } diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/settings/SettingsUpdates.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/settings/SettingsUpdates.kt index 4c45480cd1..46d32a2d2a 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/settings/SettingsUpdates.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/settings/SettingsUpdates.kt @@ -18,7 +18,7 @@ import com.lagradost.cloudstream3.mvvm.logError import com.lagradost.cloudstream3.mvvm.normalSafeApiCall import com.lagradost.cloudstream3.network.initClient import com.lagradost.cloudstream3.services.BackupWorkManager -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.ui.settings.Globals.EMULATOR import com.lagradost.cloudstream3.ui.settings.Globals.TV import com.lagradost.cloudstream3.ui.settings.SettingsFragment.Companion.getPref diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/ExtensionsFragment.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/ExtensionsFragment.kt index 1b48762939..bd1e219d04 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/ExtensionsFragment.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/ExtensionsFragment.kt @@ -28,7 +28,7 @@ import com.lagradost.cloudstream3.mvvm.observeNullable import com.lagradost.cloudstream3.plugins.RepositoryManager import com.lagradost.cloudstream3.ui.result.FOCUS_SELF import com.lagradost.cloudstream3.ui.result.setLinearListLayout -import com.lagradost.cloudstream3.ui.result.setText +import com.lagradost.cloudstream3.utils.setText import com.lagradost.cloudstream3.ui.settings.Globals.TV import com.lagradost.cloudstream3.ui.settings.Globals.isLayout import com.lagradost.cloudstream3.ui.settings.SettingsFragment.Companion.setToolBarScrollFlags diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/ExtensionsViewModel.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/ExtensionsViewModel.kt index 866d167c16..ebe9fc8886 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/ExtensionsViewModel.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/ExtensionsViewModel.kt @@ -12,8 +12,8 @@ import com.lagradost.cloudstream3.plugins.PluginManager import com.lagradost.cloudstream3.plugins.PluginManager.getPluginsOnline import com.lagradost.cloudstream3.plugins.RepositoryManager import com.lagradost.cloudstream3.plugins.RepositoryManager.PREBUILT_REPOSITORIES -import com.lagradost.cloudstream3.ui.result.UiText -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.UiText +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.utils.Coroutines.ioSafe data class RepositoryData( diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/PluginAdapter.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/PluginAdapter.kt index d159539d66..ef74851ea2 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/PluginAdapter.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/PluginAdapter.kt @@ -5,7 +5,6 @@ import android.text.format.Formatter.formatShortFileSize import android.util.Log import android.view.LayoutInflater import android.view.ViewGroup -import androidx.annotation.VisibleForTesting import androidx.appcompat.app.AppCompatActivity import androidx.core.view.isGone import androidx.core.view.isVisible @@ -18,23 +17,23 @@ import com.lagradost.cloudstream3.TvType import com.lagradost.cloudstream3.databinding.RepositoryItemBinding import com.lagradost.cloudstream3.plugins.PluginManager import com.lagradost.cloudstream3.plugins.VotingApi.getVotes -import com.lagradost.cloudstream3.ui.result.setText -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.setText +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.ui.settings.Globals.TV import com.lagradost.cloudstream3.ui.settings.Globals.isLayout import com.lagradost.cloudstream3.utils.AppContextUtils.html import com.lagradost.cloudstream3.utils.Coroutines.ioSafe import com.lagradost.cloudstream3.utils.Coroutines.main +import com.lagradost.cloudstream3.utils.ImageLoader.loadImage import com.lagradost.cloudstream3.utils.SubtitleHelper.fromTwoLettersToLanguage import com.lagradost.cloudstream3.utils.SubtitleHelper.getFlagFromIso -import com.lagradost.cloudstream3.utils.UIHelper.setImage import com.lagradost.cloudstream3.utils.UIHelper.toPx +import org.junit.Assert +import org.junit.Test import java.text.DecimalFormat import kotlin.math.floor import kotlin.math.log10 import kotlin.math.pow -import org.junit.Test -import org.junit.Assert data class PluginViewData( val plugin: Plugin, @@ -89,9 +88,7 @@ class PluginAdapter( // Clear glide image because setImageResource doesn't override override fun onViewRecycled(holder: RecyclerView.ViewHolder) { if (holder is PluginViewHolder) { - holder.binding.entryIcon.let { pluginIcon -> - com.bumptech.glide.Glide.with(pluginIcon).clear(pluginIcon) - } + holder.binding.entryIcon.loadImage(R.drawable.ic_github_logo) } super.onViewRecycled(holder) } @@ -200,20 +197,15 @@ class PluginAdapter( binding.actionSettings.isVisible = false } - if (!binding.entryIcon.setImage(//itemView.entry_icon?.height ?: + binding.entryIcon.loadImage( metadata.iconUrl?.replace( "%size%", "$iconSize" )?.replace( "%exact_size%", "$iconSizeExact" - ), - null, - errorImageDrawable = R.drawable.ic_baseline_extension_24 - ) - ) { - binding.entryIcon.setImageResource(R.drawable.ic_baseline_extension_24) - } + ) + ) { error(R.drawable.ic_baseline_extension_24) } binding.extVersion.isVisible = true binding.extVersion.text = "v${metadata.version}" diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/PluginDetailsFragment.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/PluginDetailsFragment.kt index 7d733be09e..9f0ca7ae84 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/PluginDetailsFragment.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/PluginDetailsFragment.kt @@ -19,10 +19,10 @@ import com.lagradost.cloudstream3.plugins.VotingApi.hasVoted import com.lagradost.cloudstream3.plugins.VotingApi.vote import com.lagradost.cloudstream3.utils.Coroutines.ioSafe import com.lagradost.cloudstream3.utils.Coroutines.main +import com.lagradost.cloudstream3.utils.ImageLoader.loadImage import com.lagradost.cloudstream3.utils.SubtitleHelper.fromTwoLettersToLanguage import com.lagradost.cloudstream3.utils.SubtitleHelper.getFlagFromIso import com.lagradost.cloudstream3.utils.UIHelper.colorFromAttribute -import com.lagradost.cloudstream3.utils.UIHelper.setImage import com.lagradost.cloudstream3.utils.UIHelper.toPx @@ -61,19 +61,9 @@ class PluginDetailsFragment(val data: PluginViewData) : BottomSheetDialogFragmen super.onViewCreated(view, savedInstanceState) val metadata = data.plugin.second binding?.apply { - if (!pluginIcon.setImage(//plugin_icon?.height ?: - metadata.iconUrl?.replace( - "%size%", - "$iconSize" - )?.replace( - "%exact_size%", - "$iconSizeExact" - ), - null, - errorImageDrawable = R.drawable.ic_baseline_extension_24 - ) - ) { - pluginIcon.setImageResource(R.drawable.ic_baseline_extension_24) + pluginIcon.loadImage(metadata.iconUrl?.replace("%size%", "$iconSize") + ?.replace("%exact_size%", "$iconSizeExact")) { + error(R.drawable.ic_baseline_extension_24) } pluginName.text = metadata.name.removeSuffix("Provider") pluginVersion.text = metadata.version.toString() diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/PluginsViewModel.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/PluginsViewModel.kt index fd5422b2d8..a6f9148985 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/PluginsViewModel.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/PluginsViewModel.kt @@ -19,7 +19,7 @@ import com.lagradost.cloudstream3.plugins.PluginManager import com.lagradost.cloudstream3.plugins.PluginManager.getPluginPath import com.lagradost.cloudstream3.plugins.RepositoryManager import com.lagradost.cloudstream3.plugins.SitePlugin -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.utils.Coroutines.ioSafe import com.lagradost.cloudstream3.utils.Coroutines.main import com.lagradost.cloudstream3.utils.Coroutines.runOnMainThread diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/RepoAdapter.kt b/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/RepoAdapter.kt index faf6d38bf7..f647e55339 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/RepoAdapter.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/ui/settings/extensions/RepoAdapter.kt @@ -9,7 +9,7 @@ import com.lagradost.cloudstream3.R import com.lagradost.cloudstream3.databinding.RepositoryItemBinding import com.lagradost.cloudstream3.databinding.RepositoryItemTvBinding import com.lagradost.cloudstream3.plugins.RepositoryManager.PREBUILT_REPOSITORIES -import com.lagradost.cloudstream3.ui.result.txt +import com.lagradost.cloudstream3.utils.txt import com.lagradost.cloudstream3.ui.settings.Globals.TV import com.lagradost.cloudstream3.ui.settings.Globals.isLayout import com.lagradost.cloudstream3.utils.UIHelper.clipboardHelper diff --git a/app/src/main/java/com/lagradost/cloudstream3/utils/AniSkip.kt b/app/src/main/java/com/lagradost/cloudstream3/utils/AniSkip.kt index f0c948a4a3..820a01f9f4 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/utils/AniSkip.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/utils/AniSkip.kt @@ -7,7 +7,6 @@ import com.lagradost.cloudstream3.* import com.lagradost.cloudstream3.LoadResponse.Companion.getMalId import com.lagradost.cloudstream3.mvvm.logError import com.lagradost.cloudstream3.ui.result.ResultEpisode -import com.lagradost.cloudstream3.ui.result.txt import java.lang.Long.min object EpisodeSkip { diff --git a/app/src/main/java/com/lagradost/cloudstream3/utils/BackupUtils.kt b/app/src/main/java/com/lagradost/cloudstream3/utils/BackupUtils.kt index a44af87735..7584e91247 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/utils/BackupUtils.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/utils/BackupUtils.kt @@ -29,7 +29,6 @@ import com.lagradost.cloudstream3.syncproviders.providers.MALApi.Companion.MAL_U import com.lagradost.cloudstream3.syncproviders.providers.MALApi.Companion.MAL_USER_KEY import com.lagradost.cloudstream3.syncproviders.providers.OpenSubtitlesApi.Companion.OPEN_SUBTITLES_USER_KEY import com.lagradost.cloudstream3.syncproviders.providers.SubDlApi.Companion.SUBDL_SUBTITLES_USER_KEY -import com.lagradost.cloudstream3.ui.result.txt import com.lagradost.cloudstream3.utils.Coroutines.ioSafe import com.lagradost.cloudstream3.utils.Coroutines.main import com.lagradost.cloudstream3.utils.DataStore.getDefaultSharedPrefs diff --git a/app/src/main/java/com/lagradost/cloudstream3/utils/DataStoreHelper.kt b/app/src/main/java/com/lagradost/cloudstream3/utils/DataStoreHelper.kt index 7ef7bc5760..2e16fc8c76 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/utils/DataStoreHelper.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/utils/DataStoreHelper.kt @@ -22,7 +22,6 @@ import com.lagradost.cloudstream3.syncproviders.AccountManager import com.lagradost.cloudstream3.syncproviders.SyncAPI import com.lagradost.cloudstream3.ui.WatchType import com.lagradost.cloudstream3.ui.library.ListSorting -import com.lagradost.cloudstream3.ui.result.UiImage import com.lagradost.cloudstream3.ui.result.VideoWatchState import com.lagradost.cloudstream3.utils.AppContextUtils.filterProviderByPreferredMedia import java.util.Calendar @@ -133,10 +132,7 @@ object DataStoreHelper { @JsonProperty("lockPin") val lockPin: String? = null, ) { - val image: UiImage - get() = customImage?.let { UiImage.Image(it) } ?: UiImage.Drawable( - profileImages.getOrNull(defaultImageIndex) ?: profileImages.first() - ) + val image get() = customImage?.let { UiImage.Image(it) } ?: profileImages.getOrNull(defaultImageIndex)?.let { UiImage.Drawable(it) } ?: UiImage.Drawable(profileImages.first()) } const val TAG = "data_store_helper" diff --git a/app/src/main/java/com/lagradost/cloudstream3/utils/GlideApp.kt b/app/src/main/java/com/lagradost/cloudstream3/utils/GlideApp.kt deleted file mode 100644 index 38d3fe9efc..0000000000 --- a/app/src/main/java/com/lagradost/cloudstream3/utils/GlideApp.kt +++ /dev/null @@ -1,56 +0,0 @@ -package com.lagradost.cloudstream3.utils - -import android.annotation.SuppressLint -import android.content.Context -import com.bumptech.glide.Glide -import com.bumptech.glide.GlideBuilder -import com.bumptech.glide.Registry -import com.bumptech.glide.annotation.GlideModule -import com.bumptech.glide.integration.okhttp3.OkHttpUrlLoader -import com.bumptech.glide.load.engine.DiskCacheStrategy -import com.bumptech.glide.load.engine.cache.InternalCacheDiskCacheFactory -import com.bumptech.glide.load.model.GlideUrl -import com.bumptech.glide.module.AppGlideModule -import com.bumptech.glide.request.RequestOptions -import com.bumptech.glide.signature.ObjectKey -import com.lagradost.cloudstream3.USER_AGENT -import com.lagradost.cloudstream3.network.DdosGuardKiller -import com.lagradost.cloudstream3.network.initClient -import com.lagradost.nicehttp.Requests -import java.io.InputStream - -@GlideModule -class GlideModule : AppGlideModule() { - @SuppressLint("CheckResult") - override fun applyOptions(context: Context, builder: GlideBuilder) { - super.applyOptions(context, builder) - builder.apply { - RequestOptions() - .diskCacheStrategy(DiskCacheStrategy.ALL) - .signature(ObjectKey(System.currentTimeMillis().toShort())) - }.setDiskCache { - // Possible to make this a setting in the future. - val memoryCacheSizeBytes: Long = 1024 * 1024 * 100 // 100mb - InternalCacheDiskCacheFactory(context, memoryCacheSizeBytes).build() - } - } - - // Needed for DOH - // https://stackoverflow.com/a/61634041 - override fun registerComponents(context: Context, glide: Glide, registry: Registry) { - val client = - Requests().apply { - defaultHeaders = mapOf("user-agent" to USER_AGENT) - }.initClient(context) - .newBuilder() - .addInterceptor(DdosGuardKiller(false)) - .build() - - registry.replace( - GlideUrl::class.java, - InputStream::class.java, - OkHttpUrlLoader.Factory(client) - ) - super.registerComponents(context, glide, registry) - } -} \ No newline at end of file diff --git a/app/src/main/java/com/lagradost/cloudstream3/utils/ImageModuleCoil.kt b/app/src/main/java/com/lagradost/cloudstream3/utils/ImageModuleCoil.kt new file mode 100644 index 0000000000..49ece60b5f --- /dev/null +++ b/app/src/main/java/com/lagradost/cloudstream3/utils/ImageModuleCoil.kt @@ -0,0 +1,162 @@ +package com.lagradost.cloudstream3.utils + +import android.content.Context +import android.graphics.Bitmap +import android.graphics.drawable.Drawable +import android.net.Uri +import android.util.Log +import android.widget.ImageView +import androidx.annotation.DrawableRes +import coil.EventListener +import coil.ImageLoader +import coil.load +import coil.memory.MemoryCache +import coil.request.CachePolicy +import coil.request.ErrorResult +import coil.request.ImageRequest +import coil.request.SuccessResult +import com.lagradost.cloudstream3.USER_AGENT +import com.lagradost.cloudstream3.network.DdosGuardKiller +import okhttp3.HttpUrl +import okhttp3.OkHttpClient +import java.io.File +import java.nio.ByteBuffer + +object ImageLoader { + + private var instance: ImageLoader? = null + + fun initializeCoilImageLoader(context: Context) { + if (instance == null) { + synchronized(this) { + instance = buildImageLoader(context.applicationContext) + } + } + } + + private fun buildImageLoader(context: Context): ImageLoader { + val okHttpClient = OkHttpClient.Builder() + .addInterceptor(DdosGuardKiller(alwaysBypass = false)) + .build() + + return ImageLoader.Builder(context) + .crossfade(true) + .respectCacheHeaders(false) + /** !Only use default placeholders and errors, if not using this instance for local + * image buttons because when animating this will appear or in more cases **/ + //.placeholder(R.drawable.logo) + //.error(R.drawable.logo) + .allowHardware(true) + .memoryCache { + MemoryCache.Builder(context) + .maxSizePercent(0.15) // Use 15% of the app's available memory for image caching + .build() + } + .diskCache { + coil.disk.DiskCache.Builder() + .maxSizeBytes(128 * 1024 * 1024) // 128 MB + .directory(context.cacheDir.resolve("cs3_image_cache")) + .maxSizePercent(0.02) // Use 2% of the device's storage space for disk caching + .build() + } + .diskCachePolicy(CachePolicy.ENABLED) + /** Pass interceptors with care, unnecessary passing tokens to servers + or image hosting services causes unauthorized exceptions **/ + .okHttpClient(okHttpClient) + .eventListener(object : EventListener { + override fun onStart(request: ImageRequest) { + super.onStart(request) + Log.i("CoilImageLoader", "Loading Image ${request.data}") + } + + override fun onSuccess(request: ImageRequest, result: SuccessResult) { + super.onSuccess(request, result) + Log.d("CoilImageLoader", "Image Loading successful") + } + + override fun onError(request: ImageRequest, result: ErrorResult) { + super.onError(request, result) + Log.e("CoilImageLoadError", "Error loading image: ${result.throwable}") + } + }) + .build() + } + + fun ImageView.loadImage( + imageData: UiImage?, + builder: ImageRequest.Builder.() -> Unit = {} + ) = when(imageData) { + is UiImage.Image -> loadImageInternal(imageData = imageData.url, headers = imageData.headers, builder = builder) + is UiImage.Bitmap -> loadImageInternal(imageData = imageData.bitmap, builder = builder) + is UiImage.Drawable -> loadImageInternal(imageData = imageData.resId, builder = builder) + null -> loadImageInternal(null, builder = builder) + } + + fun ImageView.loadImage( + imageData: String?, + headers: Map? = null, + builder: ImageRequest.Builder.() -> Unit = {} + ) = loadImageInternal(imageData = imageData, headers = headers, builder = builder) + + fun ImageView.loadImage( + imageData: Uri?, + headers: Map? = null, + builder: ImageRequest.Builder.() -> Unit = {} + ) = loadImageInternal(imageData = imageData,headers = headers, builder = builder) + + fun ImageView.loadImage( + imageData: HttpUrl?, + headers: Map? = null, + builder: ImageRequest.Builder.() -> Unit = {} + ) = loadImageInternal(imageData = imageData, headers = headers, builder = builder) + + fun ImageView.loadImage( + imageData: File?, + builder: ImageRequest.Builder.() -> Unit = {} + ) = loadImageInternal(imageData = imageData, builder = builder) + + fun ImageView.loadImage( + @DrawableRes imageData: Int?, + builder: ImageRequest.Builder.() -> Unit = {} + ) = loadImageInternal(imageData = imageData, builder = builder) + + fun ImageView.loadImage( + imageData: Drawable?, + builder: ImageRequest.Builder.() -> Unit = {} + ) = loadImageInternal(imageData = imageData, builder = builder) + + fun ImageView.loadImage( + imageData: Bitmap?, + builder: ImageRequest.Builder.() -> Unit = {} + ) = loadImageInternal(imageData = imageData, builder = builder) + + fun ImageView.loadImage( + imageData: ByteArray?, + builder: ImageRequest.Builder.() -> Unit = {} + ) = loadImageInternal(imageData = imageData, builder = builder) + + fun ImageView.loadImage( + imageData: ByteBuffer?, + builder: ImageRequest.Builder.() -> Unit = {} + ) = loadImageInternal(imageData = imageData, builder = builder) + + /** we use coil's built in loader with our global synchronized instance, this way we achieve + latest and complete functionality as well as stability **/ + private fun ImageView.loadImageInternal( + imageData: Any?, + headers: Map? = null, + builder: ImageRequest.Builder.() -> Unit = {} // for placeholder, error & transformations + ) { + // clear image to avoid loading issues at fast scrolling (e.g, an image recycler) + this.load(null) + + // Use Coil's built-in load method but with our custom module + this.load(imageData, instance ?: return) { + addHeader("User-Agent", USER_AGENT) + headers?.forEach { (key, value) -> + addHeader(key, value) + } + builder() // if passed + } + } +} \ No newline at end of file diff --git a/app/src/main/java/com/lagradost/cloudstream3/utils/ImageUtil.kt b/app/src/main/java/com/lagradost/cloudstream3/utils/ImageUtil.kt new file mode 100644 index 0000000000..3f9d10de43 --- /dev/null +++ b/app/src/main/java/com/lagradost/cloudstream3/utils/ImageUtil.kt @@ -0,0 +1,14 @@ +package com.lagradost.cloudstream3.utils + +import androidx.annotation.DrawableRes + +/// Type safe any image, because THIS IS NOT PYTHON +sealed class UiImage { + data class Image( + val url: String, + val headers: Map? = null + ) : UiImage() + + data class Drawable(@DrawableRes val resId: Int) : UiImage() + data class Bitmap(val bitmap: android.graphics.Bitmap) : UiImage() +} \ No newline at end of file diff --git a/app/src/main/java/com/lagradost/cloudstream3/utils/SingleSelectionHelper.kt b/app/src/main/java/com/lagradost/cloudstream3/utils/SingleSelectionHelper.kt index 70edf80c74..1801314734 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/utils/SingleSelectionHelper.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/utils/SingleSelectionHelper.kt @@ -24,9 +24,9 @@ import com.lagradost.cloudstream3.databinding.OptionsPopupTvBinding import com.lagradost.cloudstream3.ui.settings.Globals.EMULATOR import com.lagradost.cloudstream3.ui.settings.Globals.TV import com.lagradost.cloudstream3.ui.settings.Globals.isLayout +import com.lagradost.cloudstream3.utils.ImageLoader.loadImage import com.lagradost.cloudstream3.utils.UIHelper.dismissSafe import com.lagradost.cloudstream3.utils.UIHelper.popupMenuNoIconsAndNoStringRes -import com.lagradost.cloudstream3.utils.UIHelper.setImage object SingleSelectionHelper { fun Activity?.showOptionSelectStringRes( @@ -79,7 +79,7 @@ object SingleSelectionHelper { binding.imageView.apply { isGone = poster.isNullOrEmpty() - setImage(poster) + loadImage(poster) } } else { view?.popupMenuNoIconsAndNoStringRes(options.mapIndexed { index, s -> diff --git a/app/src/main/java/com/lagradost/cloudstream3/utils/SnackbarHelper.kt b/app/src/main/java/com/lagradost/cloudstream3/utils/SnackbarHelper.kt index e6a77795e3..b43b51c742 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/utils/SnackbarHelper.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/utils/SnackbarHelper.kt @@ -8,7 +8,6 @@ import com.google.android.material.snackbar.Snackbar import com.lagradost.api.Log import com.lagradost.cloudstream3.R import com.lagradost.cloudstream3.mvvm.logError -import com.lagradost.cloudstream3.ui.result.UiText import com.lagradost.cloudstream3.utils.UIHelper.colorFromAttribute object SnackbarHelper { diff --git a/app/src/main/java/com/lagradost/cloudstream3/ui/result/UiText.kt b/app/src/main/java/com/lagradost/cloudstream3/utils/TextUtil.kt similarity index 63% rename from app/src/main/java/com/lagradost/cloudstream3/ui/result/UiText.kt rename to app/src/main/java/com/lagradost/cloudstream3/utils/TextUtil.kt index 709199430b..4f3a747374 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/ui/result/UiText.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/utils/TextUtil.kt @@ -1,17 +1,13 @@ -package com.lagradost.cloudstream3.ui.result +package com.lagradost.cloudstream3.utils import android.content.Context -import android.graphics.Bitmap import android.util.Log -import android.widget.ImageView import android.widget.TextView -import androidx.annotation.DrawableRes import androidx.annotation.StringRes import androidx.core.view.isGone import androidx.core.view.isVisible import com.lagradost.cloudstream3.mvvm.logError import com.lagradost.cloudstream3.utils.AppContextUtils.html -import com.lagradost.cloudstream3.utils.UIHelper.setImage sealed class UiText { companion object { @@ -77,71 +73,6 @@ sealed class UiText { } } -sealed class UiImage { - data class Image( - val url: String, - val headers: Map? = null, - @DrawableRes val errorDrawable: Int? = null - ) : UiImage() - - data class Drawable(@DrawableRes val resId: Int) : UiImage() - data class Bitmap(val bitmap: android.graphics.Bitmap) : UiImage() -} - -fun ImageView?.setImage(value: UiImage?, fadeIn: Boolean = true) { - when (value) { - is UiImage.Image -> setImageImage(value, fadeIn) - is UiImage.Drawable -> setImageDrawable(value) - is UiImage.Bitmap -> setImageBitmap(value) - null -> { - this?.isVisible = false - } - } -} - -fun ImageView?.setImageImage(value: UiImage.Image, fadeIn: Boolean = true) { - if (this == null) return - this.isVisible = setImage(value.url, value.headers, value.errorDrawable, fadeIn) -} - -fun ImageView?.setImageDrawable(value: UiImage.Drawable) { - if (this == null) return - this.isVisible = true - this.setImage(UiImage.Drawable(value.resId)) -} - -fun ImageView?.setImageBitmap(value: UiImage.Bitmap) { - if (this == null) return - this.isVisible = true - this.setImageBitmap(value.bitmap) -} - -@JvmName("imgNull") -fun img( - url: String?, - headers: Map? = null, - @DrawableRes errorDrawable: Int? = null -): UiImage? { - if (url.isNullOrBlank()) return null - return UiImage.Image(url, headers, errorDrawable) -} - -fun img( - url: String, - headers: Map? = null, - @DrawableRes errorDrawable: Int? = null -): UiImage { - return UiImage.Image(url, headers, errorDrawable) -} - -fun img(@DrawableRes drawable: Int): UiImage { - return UiImage.Drawable(drawable) -} - -fun img(bitmap: Bitmap): UiImage { - return UiImage.Bitmap(bitmap) -} - fun txt(value: String): UiText { return UiText.DynamicString(value) } diff --git a/app/src/main/java/com/lagradost/cloudstream3/utils/UIHelper.kt b/app/src/main/java/com/lagradost/cloudstream3/utils/UIHelper.kt index ad1b6502d6..e3164301f4 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/utils/UIHelper.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/utils/UIHelper.kt @@ -13,23 +13,25 @@ import android.content.res.Configuration import android.content.res.Resources import android.graphics.Bitmap import android.graphics.Color -import android.graphics.drawable.Drawable import android.os.Build import android.os.Bundle import android.os.Handler import android.os.Looper import android.os.TransactionTooLargeException import android.util.Log -import android.view.* +import android.view.Gravity +import android.view.MenuItem +import android.view.View +import android.view.ViewGroup import android.view.ViewGroup.MarginLayoutParams +import android.view.WindowInsets +import android.view.WindowManager import android.view.inputmethod.InputMethodManager -import android.widget.ImageView import android.widget.ListAdapter import android.widget.ListView import android.widget.Toast.LENGTH_LONG import androidx.annotation.AttrRes import androidx.annotation.ColorInt -import androidx.annotation.DrawableRes import androidx.annotation.IdRes import androidx.annotation.StyleRes import androidx.appcompat.view.ContextThemeWrapper @@ -40,7 +42,6 @@ import androidx.core.content.ContextCompat import androidx.core.content.getSystemService import androidx.core.graphics.alpha import androidx.core.graphics.blue -import androidx.core.graphics.drawable.toBitmapOrNull import androidx.core.graphics.green import androidx.core.graphics.red import androidx.core.view.marginBottom @@ -53,14 +54,6 @@ import androidx.fragment.app.FragmentActivity import androidx.navigation.fragment.NavHostFragment import androidx.palette.graphics.Palette import androidx.preference.PreferenceManager -import com.bumptech.glide.load.DataSource -import com.bumptech.glide.load.engine.DiskCacheStrategy -import com.bumptech.glide.load.engine.GlideException -import com.bumptech.glide.load.model.GlideUrl -import com.bumptech.glide.load.resource.drawable.DrawableTransitionOptions -import com.bumptech.glide.request.RequestListener -import com.bumptech.glide.request.RequestOptions.bitmapTransform -import com.bumptech.glide.request.target.Target import com.google.android.material.appbar.AppBarLayout import com.google.android.material.chip.Chip import com.google.android.material.chip.ChipDrawable @@ -70,13 +63,9 @@ import com.lagradost.cloudstream3.CommonActivity.activity import com.lagradost.cloudstream3.CommonActivity.showToast import com.lagradost.cloudstream3.R import com.lagradost.cloudstream3.mvvm.logError -import com.lagradost.cloudstream3.ui.result.UiImage -import com.lagradost.cloudstream3.ui.result.UiText -import com.lagradost.cloudstream3.ui.result.txt import com.lagradost.cloudstream3.ui.settings.Globals import com.lagradost.cloudstream3.ui.settings.Globals.EMULATOR import com.lagradost.cloudstream3.ui.settings.Globals.isLayout -import jp.wasabeef.glide.transformations.BlurTransformation import kotlin.math.roundToInt object UIHelper { @@ -266,172 +255,6 @@ object UIHelper { } } - /*inline fun bindViewBinding( - inflater: LayoutInflater?, - container: ViewGroup?, - layout: Int - ): Pair { - return try { - val localInflater = inflater ?: container?.context?.let { LayoutInflater.from(it) } - ?: return null to txt( - R.string.unable_to_inflate, - "Requires inflater OR container" - )//throw IllegalArgumentException("Requires inflater OR container")) - - //println("methods: ${T::class.java.methods.map { it.name }}") - val bind = T::class.java.methods.first { it.name == "bind" } - //val inflate = T::class.java.methods.first { it.name == "inflate" } - val root = localInflater.inflate(layout, container, false) - bind.invoke(null, root) as T to null - } catch (t: Throwable) { - logError(t) - val message = txt(R.string.unable_to_inflate, t.message ?: "Primary constructor") - // if the desired layout is not found then we inflate the casted layout - /*try { - val localInflater = inflater ?: container?.context?.let { LayoutInflater.from(it) } - ?: return null to txt( - R.string.unable_to_inflate, - "Requires inflater OR container" - )//throw IllegalArgumentException("Requires inflater OR container")) - - // we don't know what method to use as there are 2, but first *should* always be true - return try { - val inflate = T::class.java.methods.first { it.name == "inflate" } - inflate.invoke(null, localInflater, container, false) as T - } catch (_: Throwable) { - val inflate = T::class.java.methods.last { it.name == "inflate" } - inflate.invoke(null, localInflater, container, false) as T - } to message - } catch (t: Throwable) { - logError(t) - }*/ - - null to message - } - }*/ - - fun ImageView?.setImage( - url: String?, - headers: Map? = null, - @DrawableRes - errorImageDrawable: Int? = null, - fadeIn: Boolean = true, - radius: Int = 0, - sample: Int = 3, - colorCallback: ((Palette) -> Unit)? = null - ): Boolean { - if (url.isNullOrBlank()) return false - this.setImage( - UiImage.Image(url, headers, errorImageDrawable), - errorImageDrawable, - fadeIn, - radius, - sample, - colorCallback - ) - return true - } - - fun ImageView?.setImage( - uiImage: UiImage?, - @DrawableRes - errorImageDrawable: Int? = null, - fadeIn: Boolean = true, - radius: Int = 0, - sample: Int = 3, - colorCallback: ((Palette) -> Unit)? = null, - ): Boolean { - if (this == null || uiImage == null) return false - - val (glideImage, identifier) = - (uiImage as? UiImage.Drawable)?.resId?.let { - it to it.toString() - } ?: (uiImage as? UiImage.Image)?.let { image -> - GlideUrl(image.url) { image.headers ?: emptyMap() } to image.url - } ?: return false - - return try { - var builder = com.bumptech.glide.Glide.with(this) - .load(glideImage) - .skipMemoryCache(true) - .diskCacheStrategy(DiskCacheStrategy.ALL).let { req -> - if (fadeIn) - req.transition(DrawableTransitionOptions.withCrossFade()) - else req - } - - if (radius > 0) { - builder = builder.apply(bitmapTransform(BlurTransformation(radius, sample))) - } - - if (colorCallback != null) { - builder = builder.listener(object : RequestListener { - - override fun onResourceReady( - resource: Drawable, - model: Any, - target: Target?, - dataSource: DataSource, - isFirstResource: Boolean - ): Boolean { - resource.toBitmapOrNull() - ?.let { bitmap -> - createPaletteAsync( - identifier, - bitmap, - colorCallback - ) - } - return false - } - - override fun onLoadFailed( - e: GlideException?, - model: Any?, - target: Target, - isFirstResource: Boolean - ): Boolean { - return false - } - }) - } - - val res = if (errorImageDrawable != null) - builder.error(errorImageDrawable).into(this) - else - builder.into(this) - res.clearOnDetach() - - true - } catch (e: Exception) { - logError(e) - false - } - } - - fun ImageView?.setImageBlur( - url: String?, - radius: Int, - sample: Int = 3, - headers: Map? = null - ) { - if (this == null || url.isNullOrBlank()) return - try { - val res = com.bumptech.glide.Glide.with(this) - .load(GlideUrl(url) { headers ?: emptyMap() }) - .apply(bitmapTransform(BlurTransformation(radius, sample))) - .transition( - DrawableTransitionOptions.withCrossFade() - ) - .skipMemoryCache(true) - .diskCacheStrategy(DiskCacheStrategy.ALL) - .into(this) - res.clearOnDetach() - } catch (e: Exception) { - logError(e) - } - } - fun adjustAlpha(@ColorInt color: Int, factor: Float): Int { val alpha = (Color.alpha(color) * factor).roundToInt() val red = Color.red(color) diff --git a/app/src/main/java/com/lagradost/cloudstream3/utils/VideoDownloadManager.kt b/app/src/main/java/com/lagradost/cloudstream3/utils/VideoDownloadManager.kt index e0b78543a2..bdaaeb2467 100644 --- a/app/src/main/java/com/lagradost/cloudstream3/utils/VideoDownloadManager.kt +++ b/app/src/main/java/com/lagradost/cloudstream3/utils/VideoDownloadManager.kt @@ -12,14 +12,16 @@ import android.util.Log import androidx.annotation.DrawableRes import androidx.core.app.NotificationCompat import androidx.core.app.NotificationManagerCompat +import androidx.core.graphics.drawable.toBitmap import androidx.core.net.toUri import androidx.preference.PreferenceManager import androidx.work.Data import androidx.work.ExistingWorkPolicy import androidx.work.OneTimeWorkRequest import androidx.work.WorkManager -import com.bumptech.glide.Glide -import com.bumptech.glide.load.model.GlideUrl +import coil.ImageLoader +import coil.request.ImageRequest +import coil.request.SuccessResult import com.fasterxml.jackson.annotation.JsonProperty import com.lagradost.cloudstream3.APIHolder.getApiFromNameNull import com.lagradost.cloudstream3.AcraApplication.Companion.removeKey @@ -52,6 +54,7 @@ import kotlinx.coroutines.cancel import kotlinx.coroutines.delay import kotlinx.coroutines.isActive import kotlinx.coroutines.launch +import kotlinx.coroutines.runBlocking import kotlinx.coroutines.sync.Mutex import kotlinx.coroutines.sync.withLock import kotlinx.coroutines.withContext @@ -59,7 +62,6 @@ import java.io.Closeable import java.io.File import java.io.IOException import java.io.OutputStream -import java.lang.IllegalArgumentException import java.util.* const val DOWNLOAD_CHANNEL_ID = "cloudstream3.general" @@ -231,15 +233,27 @@ object VideoDownloadManager { return cachedBitmaps[url] } - val bitmap = Glide.with(this) - .asBitmap() - .load(GlideUrl(url) { headers ?: emptyMap() }) - .submit(720, 720) - .get() + val imageLoader = ImageLoader(this) - if (bitmap != null) { - cachedBitmaps[url] = bitmap + val request = ImageRequest.Builder(this) + .data(url) + .apply { + headers?.forEach { (key, value) -> + addHeader(key, value) + } + } + .allowHardware(false) // Disable hardware bitmaps for compatibility + .build() + + val bitmap = runBlocking { + val result = imageLoader.execute(request) + (result as? SuccessResult)?.drawable?.toBitmap() } + + bitmap?.let { + cachedBitmaps[url] = it + } + return bitmap } catch (e: Exception) { logError(e)