天天看點

android AlertDialog TextView指派_從0系統學Android--3.7 聊天界面編寫

從0系統學Android--3.7 聊天界面編寫

android AlertDialog TextView指派_從0系統學Android--3.7 聊天界面編寫
android AlertDialog TextView指派_從0系統學Android--3.7 聊天界面編寫
本系列文章目錄

:更多精品文章分類

本系列持續更新中….

3.7 編寫界面的最佳實踐

前面學習了那麼多 UI 開發的知識,下面來進行實踐,做一個美觀的聊天界面。

3.7.1 制作 Nine-Patch 圖檔

實戰前先學習一個小知識,如何制作 Nine-Patch 圖檔。

Nine-Patch 是一種被特殊處理的

.png

圖檔,能夠指定那些區域可以被拉伸,那些區域不可以。

來看看

Nine-Patch

圖檔的實際作用。

android AlertDialog TextView指派_從0系統學Android--3.7 聊天界面編寫

首先我們用一張普通的圖檔作為背景

1<?xml version="1.0" encoding="utf-8"?>
2<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
3    android:layout_width="match_parent"
4    android:layout_height="wrap_content"
5    android:background="@mipmap/message_"
6    android:orientation="vertical">
7</LinearLayout>
           

運作結果

android AlertDialog TextView指派_從0系統學Android--3.7 聊天界面編寫

可以看到效果非常糟糕,由于圖檔的寬度不能填滿整個螢幕的寬度,整張圖檔就被均勻的拉伸的,效果很差,這種情況,我們就可以使用

Nine-Patch

圖檔來進行改善了。

如何建立

nine-patch

圖檔呢?

首先在 Android Studio 中選中你要變成

nine-patch

的圖檔,然後右擊--->Create 9-Patch file 就可以建立 Nine-Patch 圖檔了。

android AlertDialog TextView指派_從0系統學Android--3.7 聊天界面編寫

我們可以在圖檔的四個邊框繪制一個個的小黑點。在

上邊框和左邊框

的部分表示目前圖檔需要

拉伸

的時候就會拉伸黑色點标記的

區域

,在

下邊框和右邊框

的部分表示

内容會被放置的區域

。用滑鼠在圖檔的邊緣拖到就可以進行繪制了。按住

Shift

鍵拖動可以進行擦除。

再來看看使用 nine-patch 的效果

android AlertDialog TextView指派_從0系統學Android--3.7 聊天界面編寫

這樣當圖檔需要拉伸的時候就隻拉伸指定區域了。

3.7.2 編寫精美的聊天界面

聊天界面肯定有收到的消息和發送的消息,上面我們已經把發送消息的背景圖制作好了,再制作一張發送消息的背景圖。

圖檔資源都準備好了,就可以寫代碼了。

編寫首頁面布局

1<?xml version="1.0" encoding="utf-8"?>
 2<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
 3    android:layout_width="match_parent"
 4    android:layout_height="match_parent"
 5    android:orientation="vertical">
 6    <androidx.recyclerview.widget.RecyclerView
 7        android:id="@+id/rlv"
 8        android:layout_width="match_parent"
 9        android:layout_height="0dp"
10        android:layout_weight="1"/>
11    <LinearLayout
12        android:orientation="horizontal"
13        android:layout_width="match_parent"
14        android:layout_height="wrap_content">
15        <EditText
16            android:id="@+id/et_info"
17            android:layout_width="0dp"
18            android:layout_height="wrap_content"
19            android:layout_weight="1"
20            android:hint="發送資訊"
21            android:maxLines="2"/>
22        <Button
23            android:layout_width="wrap_content"
24            android:layout_height="wrap_content"
25            android:text="發送"
26            android:id="@+id/bt_send"/>
27    </LinearLayout>
28</LinearLayout>
           

建立聊天的消息對象

1public class Msg {
 2    public static final  int TYPE_RECEIVE = 0;
 3    public static final int TYPE_SEND = 1;
 4    private String content;
 5
 6    public Msg(String content, int type) {
 7        this.content = content;
 8        this.type = type;
 9    }
10
11    private int type;
12
13    public String getContent() {
14        return content;
15    }
16
17    public void setContent(String content) {
18        this.content = content;
19    }
20
21    public int getType() {
22        return type;
23    }
24
25    public void setType(int type) {
26        this.type = type;
27    }
28}
           

type 用來指定消息的類型,是發送的消息還接受的消息

然後編寫 RecyclerView 的子項布局

1<?xml version="1.0" encoding="utf-8"?>
 2<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
 3    android:layout_width="match_parent"
 4    android:layout_height="wrap_content"
 5    android:padding="10dp"
 6    android:orientation="vertical">
 7    <LinearLayout
 8        android:id="@+id/ll_left"
 9        android:background="@mipmap/message_left"
10        android:layout_width="wrap_content"
11        android:layout_height="wrap_content">
12        <TextView
13            android:layout_width="wrap_content"
14            android:layout_height="wrap_content"
15            android:layout_gravity="center"
16            android:id="@+id/tv_left"
17            android:textColor="#FFF"
18            android:layout_margin="10dp"/>
19
20    </LinearLayout>
21
22    <LinearLayout
23        android:layout_gravity="right"
24        android:id="@+id/ll_right"
25        android:background="@mipmap/message_right"
26        android:layout_width="wrap_content"
27        android:layout_height="wrap_content">
28        <TextView
29            android:layout_width="wrap_content"
30            android:layout_height="wrap_content"
31            android:layout_gravity="center"
32            android:id="@+id/tv_right"
33            android:layout_margin="10dp"/>
34
35    </LinearLayout>
36</LinearLayout>
           

這裡我們把接受消息和發送消息的布局都寫進來了,代碼中根據消息的類型來調用

visible

方法,顯示對應的消息。

建立擴充卡

1public class MsgAdapter extends RecyclerView.Adapter<MsgAdapter.MsgViewHolder> {
 2    private List<Msg> list;
 3    public MsgAdapter(List<Msg> list){
 4        this.list = list;
 5    }
 6
 7
 8
 9    class MsgViewHolder extends RecyclerView.ViewHolder{
10        LinearLayout llLeft,llRight;
11        TextView tvLeft,tvRight;
12
13        public MsgViewHolder(@NonNull View itemView) {
14            super(itemView);
15            llLeft =itemView.findViewById(R.id.ll_left);
16            llRight =itemView.findViewById(R.id.ll_right);
17            tvLeft =itemView.findViewById(R.id.tv_left);
18            tvRight =itemView.findViewById(R.id.tv_right);
19        }
20    }
21
22    @NonNull
23    @Override
24    public MsgViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
25        View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.msg_item,parent,false);
26        MsgViewHolder viewHolder = new MsgViewHolder(view);
27
28        return viewHolder;
29    }
30
31    @Override
32    public void onBindViewHolder(@NonNull MsgViewHolder holder, int position) {
33        Msg msg = list.get(position);
34        // 這裡根據消息的類型來選擇不同的布局
35        if (msg.getType() == Msg.TYPE_RECEIVE){
36            holder.llLeft.setVisibility(View.VISIBLE);
37            holder.llRight.setVisibility(View.GONE);
38            holder.tvLeft.setText(msg.getContent());
39        }else {
40            holder.llRight.setVisibility(View.VISIBLE);
41            holder.llLeft.setVisibility(View.GONE);
42            holder.tvRight.setText(msg.getContent());
43        }
44
45    }
46
47    @Override
48    public int getItemCount() {
49        return list.size();
50    }
51}
           

然後寫 Activity 代碼

1public class MsgActivity extends AppCompatActivity {
 2
 3    List<Msg> list  =new ArrayList<>();
 4    EditText text ;
 5    @Override
 6    protected void onCreate(@Nullable Bundle savedInstanceState) {
 7        super.onCreate(savedInstanceState);
 8        setContentView(R.layout.activity_nine_patch);
 9        initData();
10        final RecyclerView recyclerView  = findViewById(R.id.rlv);
11        final MsgAdapter msgAdapter = new MsgAdapter(list);
12         text = findViewById(R.id.et_info);
13        Button bt = findViewById(R.id.bt_send);
14        LinearLayoutManager layoutManager = new LinearLayoutManager(this);
15        recyclerView.setLayoutManager(layoutManager);
16        recyclerView.setAdapter(msgAdapter);
17        bt.setOnClickListener(new View.OnClickListener() {
18            @Override
19            public void onClick(View v) {
20                Random random = new Random();
21                // 這裡還是利用随機數來生成消息的類型
22                int count = random.nextInt(20);
23                Msg msg = new Msg(text.getText()+"count:"+count,count%2);
24                list.add(msg);
25                // 表示在消息的末尾插入内容
26                msgAdapter.notifyItemInserted(list.size()-1);
27                // 讓 RecyclerView 自動滾動到最底部
28                recyclerView.scrollToPosition(list.size()-1);
29                // 清空内容
30                text.setText("");
31            }
32        });
33    }
34
35    public void initData(){
36        Random random = new Random();
37        for (int i=0;i<40;i++){
38            int count = random.nextInt(20);
39            Msg msg = new Msg("消息嗯哼"+i+"count:"+count,count%2);
40            list.add(msg);
41        }
42
43
44    }
45}
           

notifyItemInserted()

方法,用于通知清單有新的資料插入了,這樣新增加的一條消息才能顯示出來。

scrolltoPosition()

方法将資料定位到最後一行,保證我們可以看到最後發送的内容。

android AlertDialog TextView指派_從0系統學Android--3.7 聊天界面編寫

繼續閱讀