如何实现Asynctask以在ArrayAdapter中加载图像

时间:2018-01-19 14:55:36

标签: java android listview android-asynctask android-arrayadapter

我正在开发一个课程列表应用程序,它通过ArrayAdapter在listview中加载每个课程标题和课程图像,我想在listview和ArrayAdapter之间实现asynctask加载图像,因为listview是滞后的滚动,请帮助我。

MainActivity.java

package com.emmakade.okt;

import android.app.Activity;
import android.content.Context;
import android.content.Intent;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.view.ViewGroup;
import android.widget.AdapterView;
import android.widget.ArrayAdapter;
import android.widget.ImageView;
import android.widget.ListView;
import android.widget.TextView;
import android.widget.Toast;

import java.util.List;

public class MainActivity extends AppCompatActivity {


    protected List<Course> data;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        data = DataProvider.getData();

        ArrayAdapter<Course> courseArrayAdapter =
                new CourseArrayAdapter(this, 0, data);
        ListView listView = (ListView) findViewById(android.R.id.list);
        listView.setAdapter(courseArrayAdapter);

        listView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
            @Override
            public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
                Course course = data.get(position);
                displayDetail(course);
            }
        });

    }


    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // Inflate the menu; this adds items to the action bar if it is present.
        getMenuInflater().inflate(R.menu.menu_main, menu);
        return true;
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        // Handle action bar item clicks here. The action bar will
        // automatically handle clicks on the Home/Up button, so long
        // as you specify a parent activity in AndroidManifest.xml.
        int id = item.getItemId();

        //noinspection SimplifiableIfStatement
        if (id == R.id.action_settings) {
            return true;
        }

        return super.onOptionsItemSelected(item);
    }

    @Override
    protected void onActivityResult(int requestCode, int resultCode, Intent data) {
        if (requestCode == DETAIL_REQUEST_CODE) {
            if (resultCode == RESULT_OK) {
                String msg = data.getStringExtra("resultMessage");
                Toast.makeText(this, msg, Toast.LENGTH_LONG).show();
            }
        }
    }

    class CourseArrayAdapter extends ArrayAdapter<Course>{

        Context context;
        List<Course> objects;

        public CourseArrayAdapter(Context context, int resource, List<Course> objects) {
            super(context, resource, objects);

            this.context = context;
            this.objects = objects;
        }

        @Override
        public View getView(int position, View convertView, ViewGroup parent) {

            Course course = objects.get(position);

            LayoutInflater inflater =
                    (LayoutInflater) context.getSystemService(Activity.LAYOUT_INFLATER_SERVICE);

            View view = inflater.inflate(R.layout.course_item, null);

            TextView tv = (TextView) view.findViewById(R.id.tvTitle);
            tv.setText(course.getTitle());

            ImageView iv = (ImageView) view.findViewById(R.id.imageCourse);
            int res = context.getResources().getIdentifier(
                    "image_" + course.getCourseNumber(), "drawable",
                    context.getPackageName()
            );
            iv.setImageResource(res);

            return view;
        }
    }
}

activity_main.xml中

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:paddingBottom="@dimen/activity_vertical_margin"
    android:paddingLeft="@dimen/activity_horizontal_margin"
    android:paddingRight="@dimen/activity_horizontal_margin"
    android:paddingTop="@dimen/activity_vertical_margin"
    tools:context=".MainActivity">

    <ImageView
        android:layout_width="100dp"
        android:layout_height="100dp"
        android:id="@+id/imageLogo"
        android:layout_alignParentStart="true"
        android:layout_alignParentTop="true"
        android:src="@drawable/academy"/>
    <TextView
        android:id="@+id/txtOutput"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="@string/course_catalog"
        android:layout_alignBottom="@+id/imageLogo"
        android:layout_toEndOf="@+id/imageLogo"
        android:layout_marginStart="20dp"
        android:layout_marginBottom="15dp"
        android:textSize="28sp" />

    <ListView
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:id="@android:id/list"
        android:layout_below="@+id/imageLogo"
        android:layout_marginTop="10dp"
        android:layout_alignParentStart="true" />

</RelativeLayout>

course_item.xml

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:padding="10dp">

    <ImageView
        android:layout_width="50dp"
        android:layout_height="50dp"
        android:id="@+id/imageCourse" />
    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:id="@+id/tvTitle"
        android:layout_toEndOf="@+id/imageCourse"
        android:layout_marginStart="10dp"
        android:textSize="18sp"/>
</RelativeLayout>

enter image description here

2 个答案:

答案 0 :(得分:0)

我建议您使用Glide库进行异步图像加载,缓存和显示。

添加依赖

invite_code

在适配器中使用这样的

implementation 'com.github.bumptech.glide:glide:4.5.0'
annotationProcessor 'com.github.bumptech.glide:compiler:4.5.0'

答案 1 :(得分:0)

您可以使用处理程序,因为asynctask可以在另一个线程上运行,但是您无法从另一个线程而不是主线程更新ui。另请考虑使用glidepicasso类库。这些库有效地缓存图像,并以更高的性能工作。

Handler有一个例子。

Handler handler = new Handler();
            handler.post(() -> {
                profilephoto.setImageBitmap(pp);
            });