android - com.bumptech.glide.Registry$NoModelLoaderAvailableException : Failed to find any ModelLoaders

标签 android android-glide

我正在尝试将自定义模型加载到 Glide 中,但出现此错误:

GlideExecutor: Request threw uncaught throwable com.bumptech.glide.Registry$NoModelLoaderAvailableException: Failed to find any ModelLoaders for model: com.company.project.glide.Movie@aac331a

Glide 版本:4.0.0

我的代码:

型号

public class Movie {
    private String name;
    private String artist;

    public Movie(String name, String artist) {
        this.name = name;
        this.artist = artist;
    }

    public String getName() {
        return name;
    }

    public String getArtist() {
        return artist;
    }
}

模块

@com.bumptech.glide.annotation.GlideModule
public class GlideModule  extends AppGlideModule {

    @Override
    public boolean isManifestParsingEnabled() {
        return false;
    }

    @Override
    public void applyOptions(Context context, GlideBuilder builder) {
        super.applyOptions(context, builder);
    }

    @Override
    public void registerComponents(Context context, Registry registry) {
        registry.append(Movie.class, InputStream.class, new MovieArtModel.Factory());
    }
}

模型加载器

public class MovieArtModel implements ModelLoader<Movie, InputStream> {

    @Nullable
    @Override
    public LoadData<InputStream> buildLoadData(Movie movie, int width, int height, Options options) {
        Timber.d("buildLoadData: ");
        return new LoadData<>(new ObjectKey(movie), new MovieArtLoader(movie, width, height));
    }


    @Override
    public boolean handles(Movie movie) {
        return false;
    }

    public static class Factory implements ModelLoaderFactory<Movie, InputStream> {

        @Override
        public ModelLoader<Movie, InputStream> build(MultiModelLoaderFactory multiFactory) {
            return new MovieArtModel();
        }

        @Override
        public void teardown() {
        }
    }


    static class MovieArtLoader implements DataFetcher<InputStream> {
        private Movie movie;
        private boolean isCancelled = false;
        private int widthSize;
        private int heightSize;

        MovieArtLoader(Movie movie, int widthSize, int heightSize) {
            Timber.d("MovieArtLoader: Initializing...width size = " + widthSize + " :: heightSize = " + heightSize);
            this.movie = movie;
            this.widthSize = widthSize;
            this.heightSize = heightSize;
        }

        @Override
        public void loadData(Priority priority, DataCallback<? super InputStream> callback) {
            Timber.d("loadData");

            //First check if request is not cancelled before starting request
            if(!isCancelled()) {
                InputStream inputStream = getMovieArtInputStream(movie);
                if (inputStream != null) {
                    callback.onDataReady(inputStream);
                } else {
                    callback.onLoadFailed(new IOException("Forced Glide network failure. Can't load Movie image"));
                }


            }
        }
            return null;
        }



        @Override public void cleanup() {
            Timber.d("cleanup: ");
        }


        @Override public void cancel() {
            Timber.d("cancel: ");
            isCancelled = true;
        }

        @Override
        public Class<InputStream> getDataClass() {
            return null;
        }

        @Override
        public DataSource getDataSource() {
            return null;
        }

        private boolean isCancelled() {
            return isCancelled;
        }
    }

然后我这样加载它:

GlideApp.with(itemView.getContext())
                .asBitmap()
                .load(new Movie(book.getMovieName(), book.getArtist()))
                .placeholder(R.drawable.movie_default_small)
                .diskCacheStrategy(DiskCacheStrategy.RESOURCE)
                .listener(this)
                .into(imageView);

请问我哪里弄错了?


编辑

我应用了下面的答案,但我开始遇到 NPE。这是堆栈跟踪:

E/GlideExecutor: Request threw uncaught throwable
                                                                        java.lang.NullPointerException: Attempt to invoke virtual method 'int java.lang.Object.hashCode()' on a null object reference
                                                                            at com.bumptech.glide.util.MultiClassKey.hashCode(MultiClassKey.java:66)
                                                                            at android.support.v4.util.SimpleArrayMap.indexOfKey(SimpleArrayMap.java:320)
                                                                            at android.support.v4.util.SimpleArrayMap.get(SimpleArrayMap.java:360)
                                                                            at com.bumptech.glide.provider.LoadPathCache.get(LoadPathCache.java:34)
                                                                            at com.bumptech.glide.Registry.getLoadPath(Registry.java:132)
                                                                            at com.bumptech.glide.load.engine.DecodeHelper.getLoadPath(DecodeHelper.java:132)
                                                                            at com.bumptech.glide.load.engine.DecodeHelper.hasLoadPath(DecodeHelper.java:128)
                                                                            at com.bumptech.glide.load.engine.SourceGenerator.startNext(SourceGenerator.java:59)
                                                                            at com.bumptech.glide.load.engine.DecodeJob.runGenerators(DecodeJob.java:282)
                                                                            at com.bumptech.glide.load.engine.DecodeJob.runWrapped(DecodeJob.java:252)
                                                                            at com.bumptech.glide.load.engine.DecodeJob.run(DecodeJob.java:222)
                                                                            at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1112)
                                                                            at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:587)
                                                                            at java.lang.Thread.run(Thread.java:818)
                                                                            at com.bumptech.glide.load.engine.executor.GlideExecutor$DefaultThreadFactory$1.run(GlideExecutor.java:347)

最佳答案

@Override
public boolean handles(Movie movie) {
    return true;
}

你需要这样做,否则 Glide 会忽略你的 ModelLoader,认为它不处理提供的 Movie 模型。

关于android - com.bumptech.glide.Registry$NoModelLoaderAvailableException : Failed to find any ModelLoaders,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45195925/

相关文章:

android - 在应用程序中实现 Samsung Galaxy Note S-Pen AirView 预览

android - Cordova/jQuery - 确定您的应用程序是在 Web/移动浏览器还是移动应用程序 (Android/iOS) 上运行

Android Glide点击item Gridview全屏显示图片

java - 我的 Android Studio 应用程序可能出现什么问题?

android - 在后台线程上的磁盘上滑动缓存图像

java - 我的工具栏太高,因此看起来很难看,并且下面的屏幕被裁剪,我该如何修复它?

android - configuration.setLocale(locale) 不适用于 AppCompatDelegate.setDefaultNightMode

Android KeyBoard 不显示在 AlertDialog 中

java - 如何记录 Glide 的每个请求 url?

android - 为什么 Glide 不会从资源 ID 加载图像到我的 ImageView?