안드로이드 개발 ViewHolder 패턴 이용해서 ListView 성능 향상하는 방법

 

환경: Android Studio

 

ViewHolder 란 특정 클래스가 아닌 성능 향상을 위한 방법론입니다. Holder 패턴을 응용한 것인데 안드로이드에서 ListView 를 구현할 때 findViewById() 함수의 호출을 줄이기 위한 저장소 입니다. ListView 를 만들려면 여러 행을 추가해야 합니다. 매번 findViewById() 함수를 호출하는 것이 아니라 ViewHolder 클래스를 만들어 각 위젯을 저장합니다. 그리고 다음에 재사용해서 ListView 의 각 행을 구현하는 것이죠.

 

ViewHolder 는 단순히 위젯을 저장하기 위한 클래스입니다. 성능이 향상되면서 스크롤이 부드러워 집니다. 매번 findViewById()를 호출하지 않아도 되기 때문입니다. ViewHolder 클래스는 다음과 같습니다

private class ViewHolder{
    TextView txtView;
    ImageView imgIcon;
}

ViewHolder 를 사용하는 곳은 Adapter 클래스의 getView() 함수가 되겠죠. 각 행을 구현하는 함수 입니다. 첫 행을 구현할 때 인수로 넘어온 View convertView null 여부를 판단해서 findViewById() 를 호출합니다. 그리고 위젯 객체는 ViewHolder 에 저장합니다. 다음 행 부터는 ViewHolder 에 저장한 값들을 참조합니다

if (convertView == null) {
    convertView = mInflater.inflate(R.layout.list_item, parent, false);
    holder = new ViewHolder();
    holder.txtView = (TextView) convertView.findViewById(R.id.txtView);
    holder.imgIcon = (ImageView) convertView.findViewById(R.id.imgIcon);

    convertView.setTag(holder);
} else {
    holder = (ViewHolder) convertView.getTag();
}

ViewHolder 를 구현한 Adapter 클래스의 전체 소스는 다음과 같습니다

import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.BaseAdapter;
import android.widget.ImageView;
import android.widget.TextView;

import com.example.gon.monitoring.R;

import java.util.ArrayList;
import java.util.List;

/**
 * Created by gon on 2017-11-14.
 */

public class PersonAdapter extends BaseAdapter {

    private Context mContext;
    private int mLayout;
    private List<Person> mItemList;
    private LayoutInflater mInflater;

    public PersonAdapter(Context context, int layout, ArrayList<Person> itemList){
        this.mContext = context;
        this.mLayout = layout;
        this.mItemList = itemList;
        this.mInflater = (LayoutInflater) context.getSystemService
                (Context.LAYOUT_INFLATER_SERVICE);
    }

    @Override
    public int getCount() {
        return 0;
    }

    @Override
    public Object getItem(int position) {
        return null;
    }

    @Override
    public long getItemId(int position) {
        return 0;
    }

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

        if (convertView == null) {
            convertView = mInflater.inflate(R.layout.list_item, parent, false);
            holder = new ViewHolder();
            holder.txtView = (TextView) convertView.findViewById(R.id.txtView);
            holder.imgIcon = (ImageView) convertView.findViewById(R.id.imgIcon);

            convertView.setTag(holder);
        } else {
            holder = (ViewHolder) convertView.getTag();
        }

        holder.txtView.setText(mItemList.get(position).getName());
        holder.imgIcon.setImageBitmap((position & 1 ) == 1 ? mIcon1 : mIcon2);

        return convertView;
    }

    private class ViewHolder{
        TextView txtView;
        ImageView imgIcon;
    }
}


저작자 표시 비영리 변경 금지
신고
Posted by 녹두장군