书小宅之android——聊天界面的实现
制作Nine-Patch图片
说明:一种被特殊处理过的图片,指定哪些区域可以被拉伸,哪些区域不可以。
从android Studio2.3开始,不再单独提供draw9patch.bat文件,要生成Nine-Patch图片文件,则在res/drawable目录下添加.png格式的图片,并且将其命名改成bubble_right.9.png形式。
双击打开图片拖拉点限定拉伸区域。
在layout文件中写入如下句子测试拉伸效果:
android:background="@drawable/bubble_right"
添加库依赖
添加RecyclerView的库依赖的参考链接
RecyclerView用法参考
在SDK manager中添加库:
常见问题解决
1、若出现依赖包冲突问题:
All com.android.support libraries must use the exact same version specification (mixing versions can lead to runtime crashes). Found versions 27.1.1, 25.3.0. Examples include com.android.support:animated-vector-drawable:27.1.1 and com.android.support:design:25.3.0 less... (Ctrl+F1)
There are some combinations of libraries, or tools and libraries, that are incompatible, or can lead to bugs. One such incompatibility is compiling with a version of the Android support libraries that is not the latest version (or in particular, a version lower than your targetSdkVersion.)
按提示加入
//noinspection GradleCompatible
2、若出现Configuration ‘compile’ is obsolete and has been replaced with ‘implementation’ and ‘api’.
的问题是因为有些配置过时,其解决方式如下:
compile 改成implementation
androidTestCompile改成androidTestImplementation
testCompile 改成testImplementation
3、若出现Failed to resolve: com.android.support:recyclerview-v7:28.0.0
,提示migrate to androidX libraries问题:
这是因为添加了不存在的依赖
在build gradle中发现此时依赖中的编译版本和配置中的依赖版本不同:
修改其中的三句话重新编译即可
compileSdkVersion 28targetSdkVersion 28
4、若出现闪退问题
教程上recyclerview写法如下,一直会出现闪退问题
<android.support.v7.widget.RecyclerViewandroid:id="@+id/msg_recycler_view"android:layout_width="match_parent"android:layout_height="0dp"android:layout_weight="1" />
如下修改代码,问题解决:
<androidx.recyclerview.widget.RecyclerViewandroid:id="@+id/msg_recycler_view"android:layout_width="match_parent"android:layout_height="0dp"android:layout_weight="1"/>
编写聊天界面
chat.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"android:orientation="vertical"android:layout_width="match_parent"android:layout_height="match_parent"android:background="#d8e0e8"><androidx.recyclerview.widget.RecyclerViewandroid:id="@+id/msg_recycler_view"android:layout_width="match_parent"android:layout_height="0dp"android:layout_weight="1"android:divider="#0000"/><LinearLayoutandroid:layout_width="match_parent"android:layout_height="wrap_content"><EditTextandroid:id="@+id/input_text"android:layout_width="0dp"android:layout_height="wrap_content"android:layout_weight="1"android:hint="Type something here"android:maxLines="2" /><Buttonandroid:id="@+id/send"android:layout_width="wrap_content"android:layout_height="wrap_content"android:text="Send" /></LinearLayout></LinearLayout>
msg_item.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"android:layout_width="match_parent"android:layout_height="wrap_content"android:orientation="vertical"android:padding="10dp"><LinearLayoutandroid:layout_width="wrap_content"android:layout_height="wrap_content"android:orientation="horizontal"><ImageViewandroid:id="@+id/head_left"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_gravity="left"android:src="@drawable/portrait1"/><LinearLayoutandroid:id="@+id/left_layout"android:layout_height="wrap_content"android:layout_width="wrap_content"android:layout_gravity="left"android:background="@drawable/bubble_left"><TextViewandroid:id="@+id/left_msg"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_gravity="center"android:layout_margin="10dp"android:textColor="#fff"/></LinearLayout></LinearLayout><LinearLayoutandroid:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_gravity="right"android:orientation="horizontal"><LinearLayoutandroid:id="@+id/right_layout"android:layout_height="wrap_content"android:layout_width="wrap_content"android:layout_gravity="right"android:background="@drawable/bubble_right"><TextViewandroid:id="@+id/right_msg"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_gravity="center"android:layout_margin="10dp"/></LinearLayout><ImageViewandroid:id="@+id/head_right"android:layout_width="wrap_content"android:layout_height="wrap_content"android:src="@drawable/portrait2"/></LinearLayout></LinearLayout>
Msg类
package com.example.wechat;public class Msg {//收到的消息public static final int TYPE_RECEIVED = 0;//发送的消息public static final int TYPE_SEND=1;private String content;private int type;public Msg(String content,int type){this.content=content;this.type=type;}public String getContent(){return content;}public int getType(){return type;}
}
MsgAdapter类
package com.example.wechat;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 java.util.List;public class MsgAdapter extends RecyclerView.Adapter<MsgAdapter.ViewHolder> {private List<Msg> mMsgList;static class ViewHolder extends RecyclerView.ViewHolder{LinearLayout leftLayout;LinearLayout rightLayout;TextView leftMsg;TextView rightMsg;ImageView protrait1;ImageView protrait2;public ViewHolder(View view){super(view);leftLayout=(LinearLayout)view.findViewById(R.id.left_layout);rightLayout=(LinearLayout)view.findViewById(R.id.right_layout);leftMsg=(TextView)view.findViewById(R.id.left_msg);rightMsg=(TextView)view.findViewById(R.id.right_msg);protrait1=(ImageView)view.findViewById(R.id.head_right);protrait2=(ImageView)view.findViewById(R.id.head_left);}}public MsgAdapter(List<Msg> msgList){mMsgList=msgList;}@Overridepublic ViewHolder onCreateViewHolder(ViewGroup parent, int viewType){//onCreateViewHolder()用于创建ViewHolder实例View view= LayoutInflater.from(parent.getContext()).inflate(R.layout.msg_item,parent,false);return new ViewHolder(view);//把加载出来的布局传到构造函数中,再返回}@Overridepublic void onBindViewHolder(ViewHolder Holder,int position){//onBindViewHolder()用于对RecyclerView子项的数据进行赋值,会在每个子项被滚动到屏幕内的时候执行Msg msg=mMsgList.get(position);if(msg.getType()==Msg.TYPE_RECEIVED){//增加对消息类的判断,如果这条消息是收到的,显示左边布局,是发出的,显示右边布局Holder.leftLayout.setVisibility(View.VISIBLE);Holder.protrait2.setVisibility(View.VISIBLE);Holder.rightLayout.setVisibility(View.GONE);Holder.protrait1.setVisibility(View.GONE);Holder.leftMsg.setText(msg.getContent());}else if(msg.getType()==Msg.TYPE_SEND) {Holder.rightLayout.setVisibility(View.VISIBLE);Holder.protrait1.setVisibility(View.VISIBLE);Holder.leftLayout.setVisibility(View.GONE);Holder.protrait2.setVisibility(View.GONE);Holder.rightMsg.setText(msg.getContent());}}@Overridepublic int getItemCount(){return mMsgList.size();}
}
Main类
package com.example.wechat;import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import androidx.appcompat.app.AppCompatActivity;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;import java.util.ArrayList;
import java.util.List;public class Main extends AppCompatActivity {private List<Msg> msgList=new ArrayList<>();private EditText inputText;private Button send;private RecyclerView msgRecyclerView;private MsgAdapter adapter;@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.chat);//初始化消息数据initMsgs();inputText=(EditText)findViewById(R.id.input_text);send=(Button)findViewById(R.id.send);msgRecyclerView=(RecyclerView)findViewById(R.id.msg_recycler_view);//LinearLayoutLayout即线性布局,创建对象后把它设置到RecyclerView当中LinearLayoutManager layoutManager=new LinearLayoutManager(this);msgRecyclerView.setLayoutManager(layoutManager);//创建MsgAdapter的实例并将数据传入到MsgAdapter的构造函数中adapter=new MsgAdapter(msgList);msgRecyclerView.setAdapter(adapter);//发送按钮点击事件send.setOnClickListener(new View.OnClickListener(){@Overridepublic void onClick(View v){//获取EditText中的内容String content=inputText.getText().toString();//内容不为空则创建一个新的Msg对象,并把它添加到msgList列表中if(!"".equals(content)){Msg msg=new Msg(content,Msg.TYPE_SEND);msgList.add(msg);//调用适配器的notifyItemInserted()用于通知列表有新的数据插入,这样新增的一条消息才能在RecyclerView中显示adapter.notifyItemInserted(msgList.size()-1);//调用scrollToPosition()方法将显示的数据定位到最后一行,以保证可以看到最后发出的一条消息msgRecyclerView.scrollToPosition(msgList.size()-1);//调用EditText的setText()方法将输入的内容清空inputText.setText("");}}});}private void initMsgs(){Msg msg1=new Msg("Hello guy.",Msg.TYPE_RECEIVED);msgList.add(msg1);Msg msg2=new Msg("Hello.Who is that?",Msg.TYPE_SEND);msgList.add(msg2);Msg msg3=new Msg("This is Tom!",Msg.TYPE_RECEIVED);msgList.add(msg3);}
}
效果演示
书小宅之android——聊天界面的实现相关推荐
- Android 聊天界面对话
转载请注明出处:http://blog.csdn.net/htwhtw123/article/details/77510010 实现Android 聊天界面对话 ,可以设计成接受到的消息在左显示,发送 ...
- 微信小程序-模仿绘制聊天界面
参考文章 1.小程序模仿微信聊天界面 2.微信小程序实现仿微信聊天界面(各种细节处理) 3.微信小程序之页面中关于聊天框三角形的制作和使用 4.仿微信聊天记录时间显示 5.微信小程序-同时获取麦克风. ...
- 书小宅之网页设计——用之有道
网页标题title:title定义的标题仅是在浏览器标题栏中显示的信息.title作为属性用来定义提示文本. 网页内容的标题hi:一般一个网页应该只有一个一级标题(主标题),也就是说网页内容应该只用依 ...
- Android 聊天界面背景图片不顶上去内容顶上去解决方法
Android 聊天界面背景图片被输入法 字数398 阅读923 评论0 喜欢14 相信做过android开发的都知道,当界面中有editText的时候,输入法可能导致把当前界面整个给顶上去,这 ...
- android聊天界面与功能,【android】聊天界面的制作-简易版实现
看完了第一行代码第三章,改进了一些基本功能,下面就听小弟一一道来: 也参考了很多别人的代码,但是总觉得一些功能可以比较轻松的实现就不绕那么多弯子,就用最基础的码代码实现一样的功能:(1)整体布局代码一 ...
- 融云android聊天界面,Android 融云IM集成以及使用详解(一)
Android 融云IM集成以及使用详解(一) 集成 1.具体的集成步骤就不在详细介绍,我们只说干货,附上融云IM官方文档地址,里面有更为详细的集成介绍 https://www.rongcloud.c ...
- Android聊天界面中图片大小的合理缩小算法
应用场景 我们知道在聊天界面中,发送显示图片是不可缺少的一部分,这个时候就会面临对于图片显示控件的缩小处理.当然如果是简单的给ImageView设置一个固定的值的话,这篇文章就没有意义了.我们要做的就 ...
- android仿抖音直播间聊天,Uni-App直播小视频|仿微信聊天界面|uniapp仿抖音
U直播是一个基于Nvue+vue+uniapp技术开发的仿抖音小视频.陌陌直播的项目.小视频及直播页面均实现了类似抖音上下滑动切换效果,还有点赞.评论.商品等功能展示. 运行效果: 技术实现:编辑器+ ...
- android聊天界面对话气泡_你在和脚本谈恋爱(自动化在IM聊天中的应用)
谢谢打开这篇文章的每个你 测开之分层自动化(Python)招生简章 Python自动化测试报告美化 在python中进行数据驱动测试 太嚣张了!他竟用Python绕过了"验证码" ...
最新文章
- 程序员面试拼多多,来看看这些面试题你掌握的有多少呢?
- c语言可移植性较差吗,c陷阱与缺陷--可移植性缺陷
- 虚拟机ubuntu19.04下设置idea快捷键
- mac安装mysql遇到的坑
- 关于CNN的权重共享,CNN到底学到了什么?
- ruby mysql 占位符_ruby操作常用数据库
- cognos的HTMl显示,cognos利用html项目和提示元素结合
- 如何带领好一个团队,管理的五条实用建议告诉你
- excel求回归直线方程的公式_如何用excel快速求线性回归方程?
- 电路设计_STM8S003F3P6 AWUADC使用小结
- 2016 安全行业全景图——By 安全牛
- python数据分析简历_帮粉丝推荐简历|Python数据分析师
- 线上问题:java.sql.SQLException: connection holder is null
- 组装台式机后进入PE,检测不到硬盘的解决方法
- CC2530(SPI)驱动FLASH芯片W25Qxx
- APP测试基本流程以及APP测试要点梳理,成功入职就靠它了
- VBA快速入门学习笔记
- webScoket即时聊天,用户不在线时消息暂存,上线立马收到
- 【转载】P2P系统频现安全漏洞 技术短板将致行业洗牌
- Nginx + VFP FastCGI开发说明
热门文章
- matlab读取xlsx文件,将大Excel(xlsx)文件加载到matlab中
- CVE-2014-6321 schannel堆溢出漏洞分析
- 项目总结(二) 网格化管理系统问题总结
- png格式图片 转 icns格式图标
- 计算机通信机房消防要求,信息机房对环境有什么要求
- 02 【uni-app起步】
- 一文掌握项目甘特图的使用方法
- 写了一个简单的画板 箭头比较难搞 虚线 虚直线 实线 实直线 椭圆 圆 正方形
- layui 怎么设置点击图片放大_layui图片如何放大
- 扇贝编程可以用c语言吗,扇贝编程手机版下载_扇贝编程app下载 v1.1.41 - 87G手游网...