从 url 加载图片

Posted

技术标签:

【中文标题】从 url 加载图片【英文标题】:Load image from url 【发布时间】:2011-08-12 05:19:08 【问题描述】:

我有一个图片网址。我想在 ImageView 中显示来自该 URL 的图像,但我无法做到。

如何做到这一点?

【问题讨论】:

How to load an ImageView by URL in android?的可能重复 看看这些问题并专注于第一个答案,在这里您可以找到两种简单而完整的方法:first method (more complete) 或second method (more simply) 您可以使用 Picasso 和 Glide 图像加载器并显示到 imageview 【参考方案1】:

如果您基于按钮单击加载图像,上面接受的答案非常好,但是如果您在新活动中执行此操作,它会使 UI 冻结一两秒钟。环顾四周,我发现一个简单的异步任务消除了这个问题。

要使用异步任务在活动结束时添加此类:

private class DownloadImageTask extends AsyncTask<String, Void, Bitmap> 
  ImageView bmImage;

  public DownloadImageTask(ImageView bmImage) 
      this.bmImage = bmImage;
  

  protected Bitmap doInBackground(String... urls) 
      String urldisplay = urls[0];
      Bitmap mIcon11 = null;
      try 
        InputStream in = new java.net.URL(urldisplay).openStream();
        mIcon11 = BitmapFactory.decodeStream(in);
       catch (Exception e) 
          Log.e("Error", e.getMessage());
          e.printStackTrace();
      
      return mIcon11;
  

  protected void onPostExecute(Bitmap result) 
      bmImage.setImageBitmap(result);
  

并使用您的 onCreate() 方法调用:

new DownloadImageTask((ImageView) findViewById(R.id.imageView1))
        .execute(MY_URL_STRING);

不要忘记在清单文件中添加以下权限

<uses-permission android:name="android.permission.INTERNET"/>

对我来说很好用。 :)

【讨论】:

我喜欢这个解决方案,你应该只清理 onPostExecute 的代码,因为它的主体已经出来了。 这很棒。 @Sofija 清理是什么意思?如果您有未知数量的图片怎么办? @5er 我在原始答案中的一些括号不合适。我已经清理了它,所以你应该可以按原样使用它。 不要忘记我们还需要在清单中添加权限: 这对于学习/黑客来说很棒(赞成)但是对于任何生产你应该使用 Imageloader 库,那里有很多。我最喜欢的是 Universal Image loader、Picasso 等。【参考方案2】:
URL url = new URL("http://image10.bizrate-images.com/resize?sq=60&uid=2216744464");
Bitmap bmp = BitmapFactory.decodeStream(url.openConnection().getInputStream());
imageView.setImageBitmap(bmp);

【讨论】:

你真的不应该使用它,因为它会阻塞 UI 线程。该库将为您处理线程和下载:github.com/koush/UrlImageViewHelper 如果你在一个单独的线程上运行该块减去 setImageBitmap,则不会 它的工作我显示在缩略图和 onclick imageview 我使用 dsplaying dailog 但它在 10 秒后打开 @koush - 如果将这段代码包裹在 AsyncTask 中就可以了。 您应该在单独的线程中进行任何网络操作,当位图加载完毕后,您可以使用 ImageView.post() 或 Handler.post()【参考方案3】:

尝试picasso nice 并在一个语句中完成

Picasso.with(context)
                .load(ImageURL)
                .resize(width,height).into(imageView);

教程: https://youtu.be/DxRqxsEPc2s

注意: Picasso.with() has been renamed to Picasso.get() 在最新版本中)

【讨论】:

毕加索、格莱德也是我的最爱。 Glide 的说法和 Picasso 很像,缓存大小有很大提升。 这应该是新的答案,尽管知道如何自己做总是很高兴。很好的文章解释了两种方式:medium.com/@crossphd/… 用于加载 url,就性能而言,Picasso 或 Glide 哪个更好?【参考方案4】:

有两种方法:

1) 使用 Glide 库 这是从 url 加载图像的最佳方式,因为当您尝试第二次显示相同的 url 时,它将从 catch 中显示,从而提高应用性能

Glide.with(context).load("YourUrl").into(imageView);

依赖:implementation 'com.github.bumptech.glide:glide:4.10.0'

2) 使用 Stream。 在这里您要从 url 图像创建位图

URL url = new URL("YourUrl");
Bitmap bitmap = BitmapFactory.decodeStream(url.openConnection().getInputStream());
imageView.setImageBitmap(bitmap);

【讨论】:

要使用 Glide,您还需要将此行添加到 Manifest.xml:当 Glide 为我工作时,我赞成你的回答。 您的“catch”应拼写为“cache”。【参考方案5】:

试试这个 添加 picasso lib jar 文件

Picasso.with(context)
                .load(ImageURL)
                .resize(width,height).noFade().into(imageView);

【讨论】:

【参考方案6】:
import java.io.IOException;
import java.io.InputStream;
import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.URL;

import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.widget.ImageView;
import android.widget.Toast;

public class imageDownload 

    Bitmap bmImg;
    void downloadfile(String fileurl,ImageView img)
    
        URL myfileurl =null;
        try
        
            myfileurl= new URL(fileurl);

        
        catch (MalformedURLException e)
        

            e.printStackTrace();
        

        try
        
            HttpURLConnection conn= (HttpURLConnection)myfileurl.openConnection();
            conn.setDoInput(true);
            conn.connect();
            int length = conn.getContentLength();
            int[] bitmapData =new int[length];
            byte[] bitmapData2 =new byte[length];
            InputStream is = conn.getInputStream();
            BitmapFactory.Options options = new BitmapFactory.Options();

            bmImg = BitmapFactory.decodeStream(is,null,options);

            img.setImageBitmap(bmImg);

            //dialog.dismiss();
             
        catch(IOException e)
        
            // TODO Auto-generated catch block
            e.printStackTrace();
//          Toast.makeText(PhotoRating.this, "Connection Problem. Try Again.", Toast.LENGTH_SHORT).show();
        


    



在您的活动中 获取图像视图并设置资源 imageDownload(url,yourImageview);

【讨论】:

【参考方案7】:

UrlImageViewHelper 将使用在 URL 中找到的图像填充 ImageView。 UrlImageViewHelper 将自动下载、保存和缓存 BitmapDrawables 中的所有图像 url。重复的 url 不会被加载到内存中两次。位图内存使用弱引用哈希表进行管理,因此一旦您不再使用图像,它将自动被垃圾收集。

UrlImageViewHelper.setUrlDrawable(imageView, "http://example.com/image.png");

https://github.com/koush/UrlImageViewHelper

【讨论】:

【参考方案8】:

基于this answer我编写了自己的加载器。

具有加载效果和外观效果:

import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.os.AsyncTask;
import android.util.DisplayMetrics;
import android.util.Log;
import android.view.Gravity;
import android.view.View;
import android.view.ViewGroup;
import android.view.animation.AlphaAnimation;
import android.view.animation.Animation;
import android.widget.FrameLayout;
import android.widget.ImageView;
import android.widget.ProgressBar;

import java.io.InputStream;

/**
 * Created by Sergey Shustikov (pandarium.shustikov@gmail.com) at 2015.
 */
public class DownloadImageTask extends AsyncTask<String, Void, Bitmap>

    public static final int ANIMATION_DURATION = 250;
    private final ImageView mDestination, mFakeForError;
    private final String mUrl;
    private final ProgressBar mProgressBar;
    private Animation.AnimationListener mOutAnimationListener = new Animation.AnimationListener()
    
        @Override
        public void onAnimationStart(Animation animation)
        

        

        @Override
        public void onAnimationEnd(Animation animation)
        
            mProgressBar.setVisibility(View.GONE);
        

        @Override
        public void onAnimationRepeat(Animation animation)
        

        
    ;
    private Animation.AnimationListener mInAnimationListener = new Animation.AnimationListener()
    
        @Override
        public void onAnimationStart(Animation animation)
        
            if (isBitmapSet)
                mDestination.setVisibility(View.VISIBLE);
            else
                mFakeForError.setVisibility(View.VISIBLE);
        

        @Override
        public void onAnimationEnd(Animation animation)
        

        

        @Override
        public void onAnimationRepeat(Animation animation)
        

        
    ;
    private boolean isBitmapSet;

    public DownloadImageTask(Context context, ImageView destination, String url)
    
        mDestination = destination;
        mUrl = url;
        ViewGroup parent = (ViewGroup) destination.getParent();
        mFakeForError = new ImageView(context);
        destination.setVisibility(View.GONE);
        FrameLayout layout = new FrameLayout(context);
        mProgressBar = new ProgressBar(context);
        FrameLayout.LayoutParams params = new FrameLayout.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);
        params.gravity = Gravity.CENTER;
        mProgressBar.setLayoutParams(params);
        FrameLayout.LayoutParams copy = new FrameLayout.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);
        copy.gravity = Gravity.CENTER;
        copy.width = dpToPx(48);
        copy.height = dpToPx(48);
        mFakeForError.setLayoutParams(copy);
        mFakeForError.setVisibility(View.GONE);
        mFakeForError.setImageResource(android.R.drawable.ic_menu_close_clear_cancel);
        layout.addView(mProgressBar);
        layout.addView(mFakeForError);
        mProgressBar.setIndeterminate(true);
        parent.addView(layout, new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT));
    

    protected Bitmap doInBackground(String... urls)
    
        String urlDisplay = mUrl;
        Bitmap bitmap = null;
        try 
            InputStream in = new java.net.URL(urlDisplay).openStream();
            bitmap = BitmapFactory.decodeStream(in);
         catch (Exception e) 
            Log.e("Error", e.getMessage());
            e.printStackTrace();
        
        return bitmap;
    

    protected void onPostExecute(Bitmap result)
    
        AlphaAnimation in = new AlphaAnimation(0f, 1f);
        AlphaAnimation out = new AlphaAnimation(1f, 0f);
        in.setDuration(ANIMATION_DURATION * 2);
        out.setDuration(ANIMATION_DURATION);
        out.setAnimationListener(mOutAnimationListener);
        in.setAnimationListener(mInAnimationListener);
        in.setStartOffset(ANIMATION_DURATION);
        if (result != null) 
            mDestination.setImageBitmap(result);
            isBitmapSet = true;
            mDestination.startAnimation(in);
         else 
            mFakeForError.startAnimation(in);
        
        mProgressBar.startAnimation(out);
    
    public int dpToPx(int dp) 
        DisplayMetrics displayMetrics = mDestination.getContext().getResources().getDisplayMetrics();
        int px = Math.round(dp * (displayMetrics.xdpi / DisplayMetrics.DENSITY_DEFAULT));
        return px;
    

添加权限

<uses-permission android:name="android.permission.INTERNET"/>

并执行:

 new DownloadImageTask(context, imageViewToLoad, urlToImage).execute();

【讨论】:

【参考方案9】:

在清单中添加 Internet 权限

<uses-permission android:name="android.permission.INTERNET" />

比创建方法如下,

 public static Bitmap getBitmapFromURL(String src) 
    try 
        Log.e("src", src);
        URL url = new URL(src);
        HttpURLConnection connection = (HttpURLConnection) url.openConnection();
        connection.setDoInput(true);
        connection.connect();
        InputStream input = connection.getInputStream();
        Bitmap myBitmap = BitmapFactory.decodeStream(input);
        Log.e("Bitmap", "returned");
        return myBitmap;
     catch (IOException e) 
        e.printStackTrace();
        Log.e("Exception", e.getMessage());
        return null;
    

现在将其添加到您的 onCreate 方法中,

 ImageView img_add = (ImageView) findViewById(R.id.img_add);


img_add.setImageBitmap(getBitmapFromURL("http://www.deepanelango.me/wpcontent/uploads/2017/06/noyyal1.jpg"));

这对我有用。

【讨论】:

【参考方案10】:

这是从 URL 显示图像的示例代码。

public static Void downloadfile(String fileurl, ImageView img) 
        Bitmap bmImg = null;
        URL myfileurl = null;
        try 
            myfileurl = new URL(fileurl);
         catch (MalformedURLException e) 
            e.printStackTrace();
        
        try 
            HttpURLConnection conn = (HttpURLConnection) myfileurl.openConnection();
            conn.setDoInput(true);
            conn.connect();
            int length = conn.getContentLength();
            if (length > 0) 
                int[] bitmapData = new int[length];
                byte[] bitmapData2 = new byte[length];
                InputStream is = conn.getInputStream();
                bmImg = BitmapFactory.decodeStream(is);
                img.setImageBitmap(bmImg);
            

         catch (IOException e) 
            e.printStackTrace();
        
    

【讨论】:

【参考方案11】:

我尝试过的最佳方法,而不是使用任何库

public Bitmap getbmpfromURL(String surl)
    try 
        URL url = new URL(surl);
        HttpURLConnection urlcon = (HttpURLConnection) url.openConnection();
        urlcon.setDoInput(true);
        urlcon.connect();
        InputStream in = urlcon.getInputStream();
        Bitmap mIcon = BitmapFactory.decodeStream(in);
        return  mIcon;
     catch (Exception e) 
        Log.e("Error", e.getMessage());
        e.printStackTrace();
        return null;
    

【讨论】:

【参考方案12】:
public class MainActivity extends Activity 

    Bitmap b;
    ImageView img;
    @Override
    protected void onCreate(Bundle savedInstanceState) 
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        img = (ImageView)findViewById(R.id.imageView1);
        information info = new information();
        info.execute("");
    

    public class information extends AsyncTask<String, String, String>
    
        @Override
        protected String doInBackground(String... arg0) 

            try
            
                URL url = new URL("http://10.119.120.10:80/img.jpg");
                InputStream is = new BufferedInputStream(url.openStream());
                b = BitmapFactory.decodeStream(is);

             catch(Exception e)
            return null;
        

        @Override
        protected void onPostExecute(String result) 
            img.setImageBitmap(b);
        
    

【讨论】:

【参考方案13】:

下面的代码向您展示了如何使用 RxAndroid 从 url 字符串设置 ImageView。 首先,添加RxAndroid library 2.0

dependencies 
    // RxAndroid
    compile 'io.reactivex.rxjava2:rxandroid:2.0.0'
    compile 'io.reactivex.rxjava2:rxjava:2.0.0'

    // Utilities
    compile 'org.apache.commons:commons-lang3:3.5'


现在使用 setImageFromUrl 设置图像。

public void setImageFromUrl(final ImageView imageView, final String urlString) 

    Observable.just(urlString)
        .filter(new Predicate<String>() 
            @Override public boolean test(String url) throws Exception 
                return StringUtils.isNotBlank(url);
            
        )
        .map(new Function<String, Drawable>() 
            @Override public Drawable apply(String s) throws Exception 
                URL url = null;
                try 
                    url = new URL(s);
                    return Drawable.createFromStream((InputStream) url.getContent(), "profile");
                 catch (final IOException ex) 
                    return null;
                
            
        )
        .filter(new Predicate<Drawable>() 
            @Override public boolean test(Drawable drawable) throws Exception 
                return drawable != null;
            
        )
        .subscribeOn(Schedulers.io())
        .observeOn(AndroidSchedulers.mainThread())
        .subscribe(new Consumer<Drawable>() 
            @Override public void accept(Drawable drawable) throws Exception 
                imageView.setImageDrawable(drawable);
            
        );

【讨论】:

【参考方案14】:
loadImage("http://relinjose.com/directory/filename.png");

给你

void loadImage(String image_location) 
    URL imageURL = null;
    if (image_location != null) 
        try 
            imageURL = new URL(image_location);         
            HttpURLConnection connection = (HttpURLConnection) imageURL
                    .openConnection();
            connection.setDoInput(true);
            connection.connect();
            InputStream inputStream = connection.getInputStream();
            bitmap = BitmapFactory.decodeStream(inputStream);// Convert to bitmap
            ivdpfirst.setImageBitmap(bitmap);
         catch (IOException e) 
            e.printStackTrace();
        
     else 
        //set any default
    

【讨论】:

ivdpfirst 是什么? xml 设计中使用的 ImageView 的 ID。【参考方案15】:

试试这个:

InputStream input = contentResolver.openInputStream(httpuri);
Bitmap b = BitmapFactory.decodeStream(input, null, options);

【讨论】:

【参考方案16】:

对我来说,Fresco 是其他库中最好的。

只需setup Fresco,然后像这样简单地设置 imageURI:

draweeView.setImageURI(uri);

查看 this 回答,解释 Fresco 的一些好处。

【讨论】:

【参考方案17】:

这是我使用 Adrian 的代码示例的工作解决方案:

private void loadImage(String pUrl) 
    Thread imageDataThread = new Thread(() -> 
        try 
            URL tUrl = new URL(pUrl);
            Bitmap imageBitmap = BitmapFactory.decodeStream(tUrl.openConnection().getInputStream());
            runOnUiThread(() -> image_preview.setImageBitmap(imageBitmap));
         catch(IOException pExc) 
            showToast("Error loading image for this question!");
            pExc.printStackTrace();
        
    );
    imageDataThread.start();

注意:您可以使用此预定义的方法来加载图像位图,也可以在需要调整图像大小或对图像进行类似操作时使用您的方法。

【讨论】:

什么是 image_preview? 这是一个 ImageView

以上是关于从 url 加载图片的主要内容,如果未能解决你的问题,请参考以下文章

nuxt 如何预加载大图片

前端页面不需要加载url获取图片

iOS:从 url 加载图像

使用后台队列从 url 加载图像仍然不够快

vue使用URL.createObjectURL() 和懒加载优化加载图片的技巧

vue使用URL.createObjectURL() 和懒加载优化加载图片的技巧