Я создал на экране чата, и я хочу отображать отправленное сообщение с левой стороны и полученные сообщения с правой стороны.
Для этого я создал два xml один для правого и один для слева, и я связал этот два xml с адаптером.
Проблема в том, что когда я отправляю текст, он находится на левой стороне, и когда я получаю текст, отправляемый текст также выравнивается с правой стороны. И когда я отправляю снова, весь текст (чат) выравнивается слева.
Вот мой ArrayAdapter:
private void setListAdapterL() {
ArrayAdapter<String> adapterL = new ArrayAdapter<String>(this,
R.layout.row_left, messages);
mList.setAdapter(adapterL);
}
private void setListAdapterR() {
// TODO Auto-generated method stub
ArrayAdapter<String> adapterR = new ArrayAdapter<String>(this,
R.layout.row_right, messages);
mList.setAdapter(adapterR);
}
Мой xml- файл для row_right.xml.in другого row_left.xml изменяется только гравитация:
<?xml version="1.0" encoding="utf-8"?>
<TextView xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@android:id/text1"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:gravity="right"
android:minHeight="?android:attr/listPreferredItemHeight"
android:paddingLeft="5dip" />
Любые идеи и предложения будут оценены.
благодаря
Для этого вам нужно создать пользовательский адаптер для представления списка вместо создания двух отдельных адаптеров для левого элемента (т.е. Отправленного элемента) и правого элемента (т.е. Полученного элемента).
Это означает, что вы управляете отправленными/полученными сообщениями в одном настраиваемом адаптере.
например,
// Sample messages inside MessageActivity
void initMessages() {
HashMap<String, String> messageSent = new HashMap<String, String>();
messageSent.put("message", "Hi");
messageSent.put("type", "sent");
messageSent.put("date", "");
HashMap<String, String> messageReceived = new HashMap<String, String>();
messageSent.put("message", "Hello");
messageSent.put("type", "received");
messageSent.put("date", "");
ArrayList<HashMap<String, String>> messages = new ArrayList<HashMap<String, String>>();
messages.add(messageSent);
messages.add(messageReceived);
MessageAdapter adapter = new MessageAdapter(mContext, messages);
setListAdapter(apater);
}
// adapter class
class MessageAdapter extends ArrayAdapter<HashMap<String, String>> {
LayoutInflater inflater;
public MessageAdapter(Context context, ArrayList<HashMap<String, String>> data) {
super(context, R.layout.raw_message, data);
inflater = (LayoutInflater) context
.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
}
public View getView(int position, View convertView, ViewGroup parent) {
ViewHolder holder;
if(convertView == null) {
convertView = inflater.inflate(R.layout.raw_message, null);
holder = new ViewHolder();
holder.txtSent = convertView.findViewByTag("sent");
holder.txtReceived = convertView.findViewByTag("received");
convertView.setTag(holder);
} else {
holder = (ViewHolder)convertView.getTag();
}
HashMap<String,String> message = getItem(position);
boolean sent = message.get("type").equals("sent");
if(sent) {
holder.txtSent.setVisibility(View.VISIBLE);
holder.txtSent.setText(message.get("message"));
holder.txtReceived.setVisibility(View.GONE);
} else {
holder.txtSent.setVisibility(View.GONE);
holder.txtReceived.setText(message.get("message"));
holder.txtReceived.setVisibility(View.VISIBLE);
}
}
class ViewHolder {
TextView txtSent;
TextView txtReceived;
}
}
// raw_message.xml
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:padding="5dp">
<TextView android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:tag="sent"/>
<TextView android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:tag="received"/>
</RelativeLayout>
Проблема в том, что когда я отправляю текст, он находится на левой стороне, и когда я получаю текст, отправляемый текст также выравнивается с правой стороны. И когда я отправляю снова, весь текст (чат) выравнивается слева.
Вероятно, это происходит потому, что каждый раз, когда вы получаете новое сообщение, вы устанавливаете новый адаптер для ListView
с новой силой тяжести (слева или справа). Поскольку новый адаптер содержит все сообщения в чате, все они выравниваются влево или вправо.
Мой совет - использовать класс объектов данных, который будет содержать фактическое сообщение + его статус (это принятое или отправленное сообщение):
class Message {
String actualMessage;
int status = 0; //(for example 0 for sent messages and 1 for received messages)
public String toString() {
return actualMessage;
}
}
Затем реализуйте свой собственный адаптер и в методе getView
посмотрите, какой тип сообщения у вас есть, и установите ориентацию для этой конкретной строки влево или вправо. Это также позволит вам просто обновлять список сообщений, а не создавать каждый раз новый объект ArrayAdapter
. Пример адаптера:
public class CustomAdapter extends ArrayAdapter<Message> {
public CustomAdapter(Context context, int resId, List<message> data) {
super(context, resId, data);
}
public View getView(int position, View convertView, ViewGroup parent) {
TextView tv = (TextView) super.getView(position, convertView, parent);
Message msg = getItem(position);
if (msg.status == 0) {
tv.setGravity(Gravity.LEFT);
} else {
tv.setGravity(Gravity.RIGHT);
}
}
}
setListAdapterL
или setListAdapterR
создания объекта Message
с obj.status = 0;
(если вы обычно вызываете setListAdapterL
) или с obj.status = 1;
(если вы обычно вызываете setListAdapterR
) и добавляете его в адаптер (возможно, также вызывайте notifydataSetChanged
).
вы столкнулись с проблемой, что все элементы всегда меняются на новый макет. Поэтому каждый раз, когда вы устанавливаете левый макет, все перемещается влево, наоборот.
Вам нужен пользовательский адаптер, который позволяет вам иметь 2 текстовых поля - один для правой и один для левой.