【问题标题】:Picasso image url lookup before load加载前毕加索图片网址查找
【发布时间】:2015-05-13 09:46:13
【问题描述】:

所以我目前正在研究用毕加索库替换项目中大量自定义图像加载AsyncTasks 的可能性,这似乎很有希望。但是,我不完全确定如何使用 Picasso 解决一个问题。

在这种情况下,我们正在下载音乐曲目的专辑封面,但是当我们的 ListView 要显示时,我们只有曲目 ID。因此,首先我们必须根据曲目 ID 查找专辑封面 URL,然后将其加载到 ImageView 中。目前我们有一个AsyncTask,我们在doInBackground()中首先查找图像URL,然后从中加载Bitmap,然后将其粘贴到onPostExecute

有什么方法可以使用 Picasso 进行这种预查找,或者我们是否必须将 Picasso 调用包装在首先执行查找的 AsyncTask 中(感觉有点违背目的)。

更新:现在的工作方式:

private class AlbumArtTask extends AsyncTask<String, Bitmap, Bitmap> {

    @Override
    protected Bitmap doInBackground(String... strings) {
        final String id = strings[0];

        // This part is what I'm asking for, basically to be able to make an Async
        // lookup of the url that will later be used by Picasso
        final Uri uri = getAlbumArtUriFromTrackId(id);

        // Creating the Bitmap and return it to be used in an ImageView
        // This part is handled by Picasso
        return bitmap = createBitmapFromUri(uri);
    }

    @Override
    protected void onPostExecute(Bitmap bitmap) {
        // load image into ImageView
    }
}

更新 2:我所追求的虚构示例

Picasso.with(mContext)
    .load(new UriProvider() {         

        // Get the actual image URI here
        public Uri getImageUri() {
            return getAlbumArtUriFromTrackId(id);
        }

     })

      // And load it here
     .into(mImageView); 

【问题讨论】:

  • 加载前查找的目的是什么?
  • 是否因为您需要位图用于其他目的?如果是这种情况,您可以在之后直接从 imageview 中获取它。
  • 预查找是什么意思?您必须显示来自本地存储的占位符,或者必须显示来自服务器的原始图像以外的预查找图像..
  • 目前正在编辑问题,但简而言之,我们正在为曲目加载专辑封面,当我们的 ListView 要显示时,我们只有曲目 ID。因此,我们首先需要根据曲目 id 查找专辑封面 url,然后将该 url 加载到 ImageView 中。
  • 如果没有找到图片,你想在查找后显示默认图片吗?

标签: android picasso


【解决方案1】:

我必须为我的应用解决同样的问题。我使用 OkHTTP 拦截器来重定向请求。

这是我的 picassa 声明:

OkHttpClient client = new OkHttpClient();
client.interceptors().add(new PhotoInterceptor());
Picasso picasso = new Picasso.Builder(context)
    .downloader(new OkHttpDownloader(client))
    .build();

这是拦截器的基本实现:

public class PhotoInterceptor implements Interceptor {

    Gson gson = new Gson();

    @Override
    public Response intercept(Chain chain) throws IOException {
        Request request = chain.request();
        Response response = chain.proceed(request);
        if (response.isSuccessful()) {
            Photo photo = gson.fromJson(response.body().charStream(), Photo.class);
            if (photo!=null) {
                request = request.newBuilder()
                    .url(photo.getPhoto_file_url())
                    .build();
                response = chain.proceed(request);
            }
        }

        return response;
    }
}

【讨论】:

  • 这只是为我返回 png 数据,我看不到获取图像 url 的方法?
【解决方案2】:

在创建 listView 时,您必须使用 Piccaso 从您的 专辑封面 URL 加载图像。然后在 Track 的 Detail 屏幕上,您必须调用您的实际图像 url 才能在 imageview 中设置它。

已编辑

private class AlbumArtTask extends AsyncTask<String, Bitmap, Uri> {

        ImageView  mImageView;
        Context mContext;    
        public AlbumArtTask(Context context,ImageView imageView){
           this.mImageView=imageView;
           this.mContext=context;

        }

                @Override 
                protected Uri doInBackground(String... strings) {
                    final String id = strings[0];

                    // This part is what I'm asking for, basically to be able to make an Async 
                    // lookup of the url that will later be used by Picasso 
                    final Uri uri = getAlbumArtUriFromTrackId(id);

                    // Creating the Bitmap and return it to be used in an ImageView 
                    // This part is handled by Picasso 
                    return uri;
                } 

                @Override 
                protected void onPostExecute(Uri uri) {

                    // You have to pass imageview in constructor.
                    // load image into ImageView 
            Picasso.with(mContext).load(uri)/* And load it here*/.into(mImageView);
                } 
            } 

【讨论】:

  • 是的,但该解决方案的问题(如果我没记错的话)是 getAlbumArtUriFromTrackId(id) 调用将在 UI 线程上进行,这是不可能的,因为 UI 上不允许网络调用线程
  • 我所追求的是在 Picasso 加载图像的同一线程上进行 URL 查找。另一种方法是创建一个 AsyncTask 然后启动 Picasso.load(..) 但我不认为这是一个好的解决方案。
  • Picasso 调用移动到 onPostExecute 会导致图像在滚动 ListView 时闪烁/最终出现在错误的位置。这是我想通过更改为 Picasso 来解决的问题之一,因为它可以解决这类问题(至少在正常加载图像时)
  • 你是从构造函数传递 imageview 到 asyncTask 还是在你的适配器类中有 AsyncTask 类?
猜你喜欢
  • 1970-01-01
  • 2020-05-12
  • 2015-02-28
  • 1970-01-01
  • 1970-01-01
  • 2015-11-16
  • 1970-01-01
  • 2020-01-15
  • 2020-07-21
相关资源
最近更新 更多