1、我们在聊天页面时候,往往会遇到,键盘、表情、其他选择切换时候页面会出现掉下来再弹起问题,这是因为,我们切换时候,键盘异步导致内容View高度变化,页面掉下来后,又被其他内容顶起这种很差视觉效果。
要解决这个问题,最简单方法就是切换时候,将内容View高度固定然后去操作键盘显示后再去释放内容View高度。
2、这里我们提供具体思路
2.1xml布局:(FrameLayout + RecyclerView,是为了让键盘弹起时候,RecyclerView有个向上平移效果)
<?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:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<!-- 标题View -->
<androidx.constraintlayout.widget.ConstraintLayout
android:layout_width="match_parent"
android:layout_height="?actionBarSize">
</androidx.constraintlayout.widget.ConstraintLayout>
<!-- 聊天展示View android:layout_weight="1" 让聊天内容填充剩下内容-->
<com.scwang.smart.refresh.layout.SmartRefreshLayout
android:id="@+id/smartRefreshLayout"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_weight="1"
app:srlEnableLoadMore="false"
app:srlEnableRefresh="true">
<!-- 添加FrameLayout 是为了让键盘弹起时候,聊天内容(RecyclerView)平移上去效果-->
<FrameLayout
android:layout_width="match_parent"
android:layout_height="match_parent">
<androidx.recyclerview.widget.RecyclerView
android:id="@+id/recyler"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_gravity="bottom"
android:overScrollMode="never"
android:scrollbars="none"
android:visibility="invisible" />
</FrameLayout>
</com.scwang.smart.refresh.layout.SmartRefreshLayout>
<!-- 按钮:发送、输入框等View -->
<LinearLayout
android:id="@+id/button_input"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical">
</LinearLayout>
<!-- 图片选择、语音、视频等View -->
<androidx.constraintlayout.widget.ConstraintLayout
android:id="@+id/other_select"
android:layout_width="match_parent"
android:layout_height="@dimen/common_dp_114"
android:visibility="gone">
</androidx.constraintlayout.widget.ConstraintLayout>
<!-- emotion 表情选择View 这个是自定义View-->
<EmotionView
android:id="@+id/emotion"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:visibility="gone" />
</LinearLayout>
2.2:当键盘需要弹起锁内容View高度(这里重点讲解参数:height,height = smartRefreshLayoutMaxHeight(聊天内容最大高度) - supportSoftInputHeight(键盘的高度),这样做的目前就是让键盘弹起时候,页面感觉聊天内容View平移上效果)
private void viewLockHeight(int height) {
LinearLayout.LayoutParams layoutParams = (LinearLayout.LayoutParams) smartRefreshLayout.getLayoutParams();
layoutParams.height = height == 0 ? smartRefreshLayout.getHeight() : height;
layoutParams.weight = 0.0F;
smartRefreshLayout.setLayoutParams(layoutParams);
}
2.3:延迟释放高度(设置 layoutParams.weight = 1.0F)
private void viewReleaseLockHeight(int delayMillis) {
if (smartRefreshLayout != null) {
smartRefreshLayout.postDelayed(new Runnable() {
@Override
public void run() {
if (smartRefreshLayout != null) {
LinearLayout.LayoutParams layoutParams = (LinearLayout.LayoutParams) smartRefreshLayout.getLayoutParams();
layoutParams.height = LinearLayout.LayoutParams.MATCH_PARENT;
layoutParams.weight = 1.0F;
smartRefreshLayout.setLayoutParams(layoutParams);
}
}
}, delayMillis == 0 ? 200L : delayMillis);
}
}
2.4:RecyclerView展示最后一条数据(切换、键盘、表情等)
public void recyclerStopScroll() {
recyclerView.stopScroll();
layoutManager.scrollToPositionWithOffset(0, 0);
}
3:切换流程
界面正常展示(此时聊天内容界面最大高度展示)--->弹起键盘
①、RecyclerView停止所有事件recyclerStopScrol()
②、内容View锁高 viewLockHeight(contentViewMaxHeight)
③、起键盘
④、延迟释放高度viewReleaseLockHeight()
弹起键盘------>表情
①、RecyclerView停止所有事件recyclerStopScrol()
②、内容View锁高 viewLockHeight(0)
③、收键盘
④、展示表情
⑤、延迟释放高度viewReleaseLockHeight()
表情------>弹起键盘
①、RecyclerView停止所有事件recyclerStopScrol()
②、内容View锁高 viewLockHeight(0)
③、弹起键盘
④、收起表情
⑤、延迟释放高度viewReleaseLockHeight()