效果展示
代码实现
activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:id="@+id/activity_main"
android:fitsSystemWindows="true"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
tools:context=".MainActivity">
<androidx.recyclerview.widget.RecyclerView
android:id="@+id/rv"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="1"
android:overScrollMode="never"
android:scrollbars="none"
android:fadeScrollbars="false"
android:dividerHeight="0dp"
android:divider="@android:color/transparent"
tools:itemCount="1"
app:layoutManager="androidx.recyclerview.widget.LinearLayoutManager" />
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:padding="5dip"
android:background="#f8f8f8"
android:gravity="center_vertical">
<ImageView
android:id="@+id/more"
android:padding="2dp"
android:layout_width="38dp"
android:layout_height="38dp"
android:layout_marginLeft="7dp"
android:layout_marginRight="7dp"
android:src="@drawable/skin_instantchat_more" />
<EditText
android:id="@+id/et"
android:layout_margin="3dip"
android:layout_width="0dip"
android:layout_weight="1.0"
android:layout_height="wrap_content"
android:maxLength="300"
android:imeOptions="actionSend"
android:inputType="textPersonName"
android:hint="输入内容" />
<TextView
android:id="@+id/btn"
android:layout_width="50dp"
android:layout_height="38dp"
android:layout_marginLeft="5dp"
android:layout_marginRight="5dp"
android:text="发送"
android:textSize="10dp"
android:textColor="@android:color/white"
android:background="@drawable/button_blue"
android:gravity="center"/>
</LinearLayout>
</LinearLayout>
item1.xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_margin="5dp"
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<LinearLayout
android:id="@+id/line1"
android:layout_alignParentRight="true"
android:background="@color/teal_200"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="vertical"
android:gravity="right|top" >
<TextView
android:id="@+id/tv_name"
android:text="ttttt"
android:layout_margin="3dp"
android:paddingRight="2dp"
android:paddingLeft="2dp"
android:padding="10dp"
android:layout_marginTop="20dp"
android:textStyle="bold"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
</LinearLayout>
</RelativeLayout>
item2.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:orientation="vertical"
android:layout_margin="5dp"
android:layout_width="wrap_content"
android:background="@color/teal_200"
android:layout_height="wrap_content">
<TextView
android:id="@+id/tv_name2"
android:text="name_xx"
android:layout_margin="2dp"
android:paddingRight="2dp"
android:paddingLeft="2dp"
android:padding="10dp"
android:layout_marginTop="20dp"
android:textStyle="bold"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
</LinearLayout>
MainActivity.java
import android.content.Context;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.view.KeyEvent;
import android.view.MotionEvent;
import android.view.View;
import android.widget.EditText;
import android.widget.TextView;
import android.widget.Toast;
import androidx.appcompat.app.AppCompatActivity;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
import java.io.IOException;
import java.net.Socket;
import java.util.ArrayList;
public class MainActivity extends AppCompatActivity {
private Context context;
private RecyclerView rv;
private EditText et;
private TextView textView;
private ArrayList<UserInfo> list;
private MyAdapter adapter;
private LinearLayoutManager manager = new LinearLayoutManager(MainActivity.this, LinearLayoutManager.VERTICAL, false);
private long exitTime = 0;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
//去掉顶部标题
getSupportActionBar().hide();
setContentView(R.layout.activity_main);
context = this;
rv = (RecyclerView) findViewById(R.id.rv);
et = (EditText) findViewById(R.id.et);
textView = (TextView) findViewById(R.id.btn);
list = new ArrayList<>();
adapter = new MyAdapter(this);
textView.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
String data = et.getText().toString();
UserInfo user = null;
if(list.size()%2 == 0){
user = new UserInfo(data,2,"");
}
else {
user = new UserInfo(data,1,"");
}
list.add(user);
// 向适配器set数据
adapter.setData(user);
rv.setAdapter(adapter);
//rv.setScaleY(-1);//必须设置
//LinearLayoutManager manager = new LinearLayoutManager(MainActivity.this, LinearLayoutManager.VERTICAL, false);
manager.setOrientation(LinearLayoutManager.VERTICAL);
// manager.setStackFromEnd(true);
rv.setLayoutManager(manager);
et.setText("");
}
});
et.setOnTouchListener(new View.OnTouchListener() {
@Override
public boolean onTouch(View view, MotionEvent motionEvent) {
//滚动到底部
manager.scrollToPositionWithOffset(list.size()-1,0);
return false;
}
});
}
@Override
public boolean onKeyDown(int keyCode, KeyEvent event) {
if(keyCode == KeyEvent.KEYCODE_BACK && event.getAction() == KeyEvent.ACTION_DOWN){
if((System.currentTimeMillis()-exitTime) > 2000){
Toast.makeText(getApplicationContext(), "再按一次退出程序", Toast.LENGTH_SHORT).show();
exitTime = System.currentTimeMillis();
} else {
finish();
System.exit(0);
}
return true;
}
return super.onKeyDown(keyCode, event);
}
}
MyAdapter.java
import android.content.Context;
import android.database.DataSetObservable;
import android.util.DisplayMetrics;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.TextView;
import androidx.recyclerview.widget.RecyclerView;
import com.bumptech.glide.Glide;
import java.util.ArrayList;
public class MyAdapter extends RecyclerView.Adapter {
private Context context;
private ArrayList<UserInfo> data;
private static final int TYPEONE = 1;
private static final int TYPETWO = 2;
public MyAdapter(Context context) {
this.context = context;
data = new ArrayList<>();
}
public void setData(UserInfo data) {
this.data.add(data);
notifyDataSetChanged();
}
@Override
public int getItemViewType(int position) {
int dataType = data.get(position).getDataType();
return dataType;
}
@Override
public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
RecyclerView.ViewHolder holder = null;
switch (viewType){
case TYPEONE:
View view = LayoutInflater.from(context).inflate(R.layout.item1,parent,false);
holder = new OneViewHolder(view);
break;
case TYPETWO:
View view1 = LayoutInflater.from(context).inflate(R.layout.item2,parent,false);
holder = new TwoViewHolder(view1);
break;
}
return holder;
}
@Override
public void onBindViewHolder(RecyclerView.ViewHolder holder, int position) {
int itemViewType = getItemViewType(position);
switch (itemViewType){
case TYPEONE:
OneViewHolder oneViewHolder = (OneViewHolder) holder;
oneViewHolder.name1.setText((String)data.get(position).getData());
break;
case TYPETWO:
TwoViewHolder twoViewHolder = (TwoViewHolder) holder;
twoViewHolder.name2.setText((String)data.get(position).getData());
break;
}
}
@Override
public int getItemCount() {
return data != null && data.size() > 0 ? data.size() : 0;
}
class OneViewHolder extends RecyclerView.ViewHolder{
private TextView name1;
public OneViewHolder(View itemView) {
super(itemView);
name1 = (TextView) itemView.findViewById(R.id.tv_name);
}
}
class TwoViewHolder extends RecyclerView.ViewHolder{
private TextView name2;
public TwoViewHolder(View itemView) {
super(itemView);
name2 = (TextView) itemView.findViewById(R.id.tv_name2);
}
}
}
UserInfo.java
import java.io.Serializable;
public class UserInfo implements Serializable {
/**
* 内容
*/
private Object data;
/**
* 内容类型 1---自己 , 2------对方
*/
private int dataType ;
/**
* 时间
*/
private String time;
public UserInfo(){
}
public UserInfo(String data, int dataType, String time){
this.data = data;
this.dataType = dataType;
this.time = time;
}
public Object getData() {
return data;
}
public void setData(String data) {
this.data = data;
}
public int getDataType() {
return dataType;
}
public void setDataType(int dataType) {
this.dataType = dataType;
}
public String getTime() {
return time;
}
public void setTime(String time) {
this.time = time;
}
@Override
public String toString() {
return "UserInfo{" +
"data=" + data +
", dataType=" + dataType +
", time='" + time + '\'' +
'}';
}
}