Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/315.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/vim/5.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java Android-异步下载图像并显示它_Java_Android - Fatal编程技术网

Java Android-异步下载图像并显示它

Java Android-异步下载图像并显示它,java,android,Java,Android,这是代码,图像确实已下载,但问题是我无法显示它,因为无法解析方法findViewById public class ImageDownloader extends AsyncTask<String, Integer, Bitmap> { protected void onPreExecute(){ //Setup is done here } @Override protected Bitmap doInBackground(String... params) {

这是代码,图像确实已下载,但问题是我无法显示它,因为无法解析方法findViewById

public class ImageDownloader
    extends AsyncTask<String, Integer, Bitmap> {

protected void onPreExecute(){
    //Setup is done here
}
@Override
protected Bitmap doInBackground(String... params) {
    //this where i get the image using HttpURLConnection 
}
protected void onProgressUpdate(Integer... params){
    //Update a progress bar here, or ignore it, it's up to you
}
protected void onPostExecute(Bitmap img){
    //here is the problem with findViewById beeing undefined
    ImageView image_view = (ImageView) findViewById(R.id.remote_image);

    if(image_view!=null && img!=null){
        image_view.setImageBitmap(img);
    }
}

`

要访问
findViewById
,您需要实际视图。只能在
活动
片段
视图
类中使用该方法

传递引用,不要做你的类不应该做的事情:

// add the constructor
public ImageDownloader(ImageView image) {
    mImage = image;
}
然后调用构造函数:

ImageDownloader download = new ImageDownloader((ImageView) findViewById(R.id.remote_image));
清洁的解决方案还应使用
WeakReference
而不是
ImageView
,因为在长时间运行的任务中保留引用可能会导致内存泄漏


使用
AsyncTask
作为非静态内部类不会防止同样的问题,因为它还会保留对活动的引用,从而导致所述内存泄漏。

您需要在活动中将您的
imageview
声明为字段

在创建时初始化它

private ImageView image_view;

@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.main);
    image_view = (ImageView) findViewById(R.id.remote_image);
    ImageDownloader download = new ImageDownloader();
    download.execute("http://wanderingoak.net/bridge.png");
}
您的异步任务:

public class ImageDownloader
    extends AsyncTask<String, Integer, Bitmap> {

    protected void onPreExecute(){
        //Setup is done here
    }

    @Override
    protected Bitmap doInBackground(String... params) {
        //this where i get the image using HttpURLConnection 
    }

    protected void onProgressUpdate(Integer... params){
        //Update a progress bar here, or ignore it, it's up to you
    }

    protected void onPostExecute(Bitmap img){
        if(image_view!=null && img!=null){
            image_view.setImageBitmap(img);
        }
    }
公共类ImageDownloader
扩展异步任务{
受保护的void onPreExecute(){
//安装在这里完成
}
@凌驾
受保护位图doInBackground(字符串…参数){
//这是我使用HttpURLConnection获取图像的地方
}
受保护的void onProgressUpdate(整数…参数){
//在这里更新进度条,或者忽略它,这取决于您
}
受保护的void onPostExecute(位图img){
如果(图像视图!=null&&img!=null){
图像视图。设置图像位图(img);
}
}

Android开发者页面提供了许多有用的示例:

我假设您在处理多个下载图像方面做得不错。但如果是这样,那么您的异步任务应该检查是否存在对imageView的引用。 你应该朝这个方向走:

public class ImageDownloader extends AsyncTask<String, Integer, Bitmap> {

        private final WeakReference<ImageView> imageViewReference;

        public ImageDownloader(ImageView imageView) {
            imageViewReference = new WeakReference<ImageView>(imageView);
        }

        protected void onPreExecute() {
            //Setup is done here
        }

        @Override
        protected Bitmap doInBackground(String... params) {
            //this where i get the image using HttpURLConnection
        }

        protected void onProgressUpdate(Integer... params) {
            //Update a progress bar here, or ignore it, it's up to you
        }

        protected void onPostExecute(Bitmap bitmap) {

            if (imageViewReference != null && bitmap != null) {
                final ImageView imageView = imageViewReference.get();
                if (imageView != null) {
                    imageView.setImageBitmap(bitmap);
                }
            }
        }
    }

remote\u image
是您当前布局中图像视图的id吗?显然asynctask没有这样的方法…显然您必须将imageview引用传递给它,或者使您的asynctask实现成为具有这样的方法的类的内部非静态类…看起来缺少java的基础知识(根本没有与android连接)不要重新发明轮子。使用。你需要向
ImageDownloader
添加一个构造函数,它将
活动
作为参数…或者更好的是,使用
ImageView
@cricket\u 007我同意第三方库对这一点很好,特别是在开发时间非常关键的情况下。同时,使用异步任务来完成这一点self是一个很好的学习练习,并不完全是琐碎的。OP在尝试设置其映像之前,还必须注意不要破坏
ImageView
。@代码学徒不会在最坏的情况下泄露活动吗?你是对的,一个
WeakReference
将是一个不错的选择,但我不想过度训练OP。我不是100%满意e关于这里的生命周期问题。如果
AsyncTask
启动,然后用户导航到另一个活动/片段,最后
AsyncTask
完成并设置
ImageView
的映像,会发生什么情况?
ImageDownloader
中的引用是否有效?尝试过这个方法并确实有效,但这是正确的吗r方法?@Akis\u Tfs根据您的情况,可以有很多方法,但我认为在您的情况下,imageview应该是活动的属性,无需将其传递给AsyncTask。您应该包含封闭的类声明,以使答案更清楚。@Code peduate like?哪个类包含onCreate()?那么
ImageDownloader
如何访问
image\u视图
?异步任务应该是活动的一部分,然后它可以访问活动的该字段,这当然是一个解决方案。您的答案可以通过显式显示来改进。这肯定很有效,对我帮助很大。如果我想在e图像正在下载?@Akis\u Tfs,只需使用,它更易于使用,让您轻松完成。
public class ImageDownloader extends AsyncTask<String, Integer, Bitmap> {

        private final WeakReference<ImageView> imageViewReference;

        public ImageDownloader(ImageView imageView) {
            imageViewReference = new WeakReference<ImageView>(imageView);
        }

        protected void onPreExecute() {
            //Setup is done here
        }

        @Override
        protected Bitmap doInBackground(String... params) {
            //this where i get the image using HttpURLConnection
        }

        protected void onProgressUpdate(Integer... params) {
            //Update a progress bar here, or ignore it, it's up to you
        }

        protected void onPostExecute(Bitmap bitmap) {

            if (imageViewReference != null && bitmap != null) {
                final ImageView imageView = imageViewReference.get();
                if (imageView != null) {
                    imageView.setImageBitmap(bitmap);
                }
            }
        }
    }
@Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        ImageView iv = (ImageView) findViewById(R.id.myImageView);
        new ImageDownloader(iv).execute("http://wanderingoak.net/bridge.png");
    }