Android: 通过滑动下载绘图

Android: Download drawable via glide

我正在尝试更换适配器中的 radiobutton.buttonDrawable。从我的 drawable 文件夹中选择静态 drawables 是可行的。我现在想要的是从我的 cloud-firestore-storage 下载可绘制对象(.svg 文件),将它们转换为可绘制对象并将它们设置为单选按钮。

我当前的实现不起作用,因为它什么都不做(不改变任何东西)。我已经检查了网址 (getItem(position).icon),它们似乎是正确的。

当前方法

class ShopFilterItemAdapter @Inject constructor(
    // @ApplicationContext private val context: Context
) : ListAdapter<ShopFilterCategory, ShopFilterItemAdapter.ShopFilterViewHolder>(Companion) {
    private var checkedRadioButton: CompoundButton? = null
    var defaultCheckedId: Int = 0
    private lateinit var listener: OnItemSelectedListener

    companion object: DiffUtil.ItemCallback<ShopFilterCategory>() {
        override fun areItemsTheSame(oldItem: ShopFilterCategory, newItem: ShopFilterCategory): Boolean = oldItem === newItem
        override fun areContentsTheSame(oldItem: ShopFilterCategory, newItem: ShopFilterCategory): Boolean = oldItem == newItem
    }

    inner class ShopFilterViewHolder(val binding: ShopFilterListItemBinding) : RecyclerView.ViewHolder(binding.root)

    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ShopFilterViewHolder {
        val layoutInflater = LayoutInflater.from(parent.context)
        val binding = ShopFilterListItemBinding.inflate(layoutInflater, parent, false)
        return ShopFilterViewHolder(binding)
    }

    override fun onBindViewHolder(holder: ShopFilterViewHolder, position: Int) {
        holder.binding.filterItem = getItem(position)

        if (checkedRadioButton == null && defaultCheckedId == position) holder.binding.rbItem.isChecked = true
        
        if (holder.binding.rbItem.isChecked) checkedRadioButton = holder.binding.rbItem

        // Trying to load the images here
        Glide.with(holder.binding.root)
            .asDrawable()
            .load(getItem(position).icon)
            .into(object : CustomTarget<Drawable>() {
                override fun onResourceReady(resource: Drawable, transition: Transition<in Drawable>?) {
                    holder.binding.rbItem.buttonDrawable = resource
                }

                override fun onLoadCleared(placeholder: Drawable?) {
                    TODO("Not yet implemented")
                }

            })

        holder.binding.executePendingBindings()
    }

编辑

我错了一部分,它抛出了一个错误:

java.io.IOException: java.lang.RuntimeException: setDataSourceCallback failed: status = 0x80000000
    at com.bumptech.glide.load.resource.bitmap.VideoDecoder.decode(VideoDecoder.java:185)
    at com.bumptech.glide.load.engine.DecodePath.decodeResourceWithList(DecodePath.java:92)
    at com.bumptech.glide.load.engine.DecodePath.decodeResource(DecodePath.java:70)
    at com.bumptech.glide.load.engine.DecodePath.decode(DecodePath.java:59)
    at com.bumptech.glide.load.engine.LoadPath.loadWithExceptionList(LoadPath.java:76)
    at com.bumptech.glide.load.engine.LoadPath.load(LoadPath.java:57)
    at com.bumptech.glide.load.engine.DecodeJob.runLoadPath(DecodeJob.java:524)
    at com.bumptech.glide.load.engine.DecodeJob.decodeFromFetcher(DecodeJob.java:488)
    at com.bumptech.glide.load.engine.DecodeJob.decodeFromData(DecodeJob.java:474)
    at com.bumptech.glide.load.engine.DecodeJob.decodeFromRetrievedData(DecodeJob.java:426)
    at com.bumptech.glide.load.engine.DecodeJob.onDataFetcherReady(DecodeJob.java:390)
    at com.bumptech.glide.load.engine.SourceGenerator.onDataFetcherReady(SourceGenerator.java:176)
    at com.bumptech.glide.load.engine.DataCacheGenerator.onDataReady(DataCacheGenerator.java:94)
    at com.bumptech.glide.load.model.ByteBufferFileLoader$ByteBufferFetcher.loadData(ByteBufferFileLoader.java:70)
    at com.bumptech.glide.load.engine.DataCacheGenerator.startNext(DataCacheGenerator.java:74)
    at com.bumptech.glide.load.engine.SourceGenerator.startNext(SourceGenerator.java:50)
    at com.bumptech.glide.load.engine.DecodeJob.runGenerators(DecodeJob.java:310)
    at com.bumptech.glide.load.engine.DecodeJob.runWrapped(DecodeJob.java:279)
    at com.bumptech.glide.load.engine.DecodeJob.run(DecodeJob.java:234)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1167)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:641)
    at java.lang.Thread.run(Thread.java:919)
    at com.bumptech.glide.load.engine.executor.GlideExecutor$DefaultThreadFactory.run(GlideExecutor.java:393)
 Caused by: java.lang.RuntimeException: setDataSourceCallback failed: status = 0x80000000
    at android.media.MediaMetadataRetriever._setDataSource(Native Method)
    at android.media.MediaMetadataRetriever.setDataSource(MediaMetadataRetriever.java:210)
    at com.bumptech.glide.load.resource.bitmap.VideoDecoder$ByteBufferInitializer.initialize(VideoDecoder.java:316)
    at com.bumptech.glide.load.resource.bitmap.VideoDecoder$ByteBufferInitializer.initialize(VideoDecoder.java:310)
    at com.bumptech.glide.load.resource.bitmap.VideoDecoder.decode(VideoDecoder.java:173)
    at com.bumptech.glide.load.engine.DecodePath.decodeResourceWithList(DecodePath.java:92) 
    at com.bumptech.glide.load.engine.DecodePath.decodeResource(DecodePath.java:70) 
    at com.bumptech.glide.load.engine.DecodePath.decode(DecodePath.java:59) 
    at com.bumptech.glide.load.engine.LoadPath.loadWithExceptionList(LoadPath.java:76) 
    at com.bumptech.glide.load.engine.LoadPath.load(LoadPath.java:57) 
    at com.bumptech.glide.load.engine.DecodeJob.runLoadPath(DecodeJob.java:524) 
    at com.bumptech.glide.load.engine.DecodeJob.decodeFromFetcher(DecodeJob.java:488) 
    at com.bumptech.glide.load.engine.DecodeJob.decodeFromData(DecodeJob.java:474) 
    at com.bumptech.glide.load.engine.DecodeJob.decodeFromRetrievedData(DecodeJob.java:426) 
    at com.bumptech.glide.load.engine.DecodeJob.onDataFetcherReady(DecodeJob.java:390) 
    at com.bumptech.glide.load.engine.SourceGenerator.onDataFetcherReady(SourceGenerator.java:176) 
    at com.bumptech.glide.load.engine.DataCacheGenerator.onDataReady(DataCacheGenerator.java:94) 
    at com.bumptech.glide.load.model.ByteBufferFileLoader$ByteBufferFetcher.loadData(ByteBufferFileLoader.java:70) 
    at com.bumptech.glide.load.engine.DataCacheGenerator.startNext(DataCacheGenerator.java:74) 
    at com.bumptech.glide.load.engine.SourceGenerator.startNext(SourceGenerator.java:50) 
    at com.bumptech.glide.load.engine.DecodeJob.runGenerators(DecodeJob.java:310) 
    at com.bumptech.glide.load.engine.DecodeJob.runWrapped(DecodeJob.java:279) 
    at com.bumptech.glide.load.engine.DecodeJob.run(DecodeJob.java:234) 
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1167) 
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:641) 
    at java.lang.Thread.run(Thread.java:919) 
    at com.bumptech.glide.load.engine.executor.GlideExecutor$DefaultThreadFactory.run(GlideExecutor.java:393) 

我已经设法解决了这个问题,不幸的是,用滑行是不可能的,但是用线圈是不可能的。

1。添加必要的依赖项

implementation "io.coil-kt:coil-base:1.1.0" // or "io.coil-kt:coil-1.1.0" if you don't want to use dependency Injection
implementation "io.coil-kt:coil-svg:1.1.0"

2。构建 ImageLoader Singleton 并添加 SVGEndoder

@Provides
@Singleton
fun provideImageLoader(@ApplicationContext context: Context) = ImageLoader.Builder(context)
    .componentRegistry { add(SvgDecoder(context)) }
    .build()

3.Build 请求

fun buildRequest(context: Context, data: Any, target: RadioButton) = ImageRequest.Builder(context)
    .data(data)
    .target { drawable -> target.buttonDrawable = drawable }
    .size(64, 60) // unfortunately I was not able to get the default radiobutton.drawable size here
    .build()

4。适配器内部

override fun onBindViewHolder(holder: YourHolder, position: Int) {

   val newRequest = shopFilterValidator.buildRequest(
       context = holder.binding.rbItem.context,
       data = getItem(position).icon, // here a url from firebase
       target = holder.binding.rbItem
   )

   imageLoader.enqueue(newRequest)
}

这会将 svg 图像加载为可绘制对象并将它们作为 radiobutton.drawable