2

わかりました、以前の同様の質問を削除して、きれいに保つことに投票しました。ListView問題:チャット アプリでメッセージを表示するためのカスタムを使用しようとしています。ユーザーの入力に従ってテキストを設定することができましたが、getView()メソッドにいくつかの問題があります。下の写真で問題を確認できます。膨張したレイアウトが間違った位置に追加されています。

ここに画像の説明を入力

これは test で始まり、test5 で終わる必要があります。6行が膨張したので、getView()メソッドは6回呼び出されるべきだったと思いますか? しかし、このメソッドにログを追加したところ、20 回以上呼び出されていることがわかりました。なんでそうなの?

ここに画像の説明を入力

私のコードは以下になります:

アダプタ クラス:

public final class ChatAdapter extends BaseAdapter {
private Context context;
ViewHolder holder;

private ArrayList<String> messages;

public ChatAdapter(Context context, ArrayList<String> chat) {

    this.context = context;
    this.messages = chat;
    Log.d("ChatAdapter", "called constructor");

}

public int getCount() {
    return messages.size();
}

public Object getItem(int position) {
    return messages.get(position);
}

public long getItemId(int position) {
    return position;
}

public View getView(int position, View convertView, ViewGroup viewGroup) {

    if (convertView == null) {
        LayoutInflater inflater = (LayoutInflater) context
                .getSystemService(Context.LAYOUT_INFLATER_SERVICE);
        convertView = inflater.inflate(R.layout.row, null);

        holder = new ViewHolder();
        holder.message = (TextView) convertView
                .findViewById(R.id.tvMessage);
        holder.timestamp = (TextView) convertView.findViewById(R.id.tvTS);
        holder.indicator = (ImageView) convertView
                .findViewById(R.id.imgInd);

        String message = (String) getItem(position);
        holder.message.setText(message);
        holder.timestamp.setText(generateTimestamp());

        convertView.setTag(holder);

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

    }
    Log.d("ChatAdapter", "called getView");
    return convertView;
}

@SuppressLint("SimpleDateFormat")
public String generateTimestamp() {
    SimpleDateFormat sdf = new SimpleDateFormat("HH:mm");
    String ts = sdf.format(new Date());

    return ts;
}

public static class ViewHolder {
    public TextView message;
    public TextView timestamp;
    public ImageView indicator;
}

チャットアクティビティ:

public class ChatActivity extends ListActivity {

private EditText input;
private String tmpMessage;
ListView lv;
ChatAdapter adapter;
ArrayList<String> messages;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.lis);
    Button send = (Button) findViewById(R.id.btnSend);
    input = (EditText) findViewById(R.id.etInput);
    lv = getListView();

    messages = new ArrayList<String>();
    Log.d("Chat", "arrayList created");
    adapter = new ChatAdapter(this, messages);
    lv.setOnItemClickListener(new OnItemClickListener() {

        @Override
        public void onItemClick(AdapterView<?> arg0, View arg1, int arg2,
                long arg3) {
            // TODO
        }
    });

    lv.setAdapter(adapter);

    send.setOnClickListener(new View.OnClickListener() {

        @Override
        public void onClick(View v) {
            sendMessage();
        }
    });
}

public void sendMessage() {

    tmpMessage = input.getText().toString();
    input.setText("");


    messages.add(tmpMessage);

    adapter.notifyDataSetChanged();

}

何が欠けていますか (一部の脳を除く)? どんな助けでも大歓迎です。

4

1 に答える 1

1

6行が膨らんだのでgetView()メソッドを6回呼び出す必要があったと思いますか?しかし、私はこのメソッドにログを追加し、それが20回以上呼び出されていることを理解しました!なぜそうなのか?

強制的getView()に複数回呼び出される一般的な原因wrap_contentは、ListViewの高さを使用することです。

また、このコードはgetView()

String message = (String) getItem(position);
holder.message.setText(message);
holder.timestamp.setText(generateTimestamp()); // You will need to make a permanent timestamp someday

スクロールをサポートするには、if-elseブロックの外側にある必要があります。

于 2013-01-26T17:27:23.630 に答える