最近写了一个项目 遇到一些问题卡了我一段时间 记录下来
先说下我要实现的效果
1、我先选择的是监听软键盘的弹出和收回 根据不同的回调执行对应的方法
由于代码执行失败 已经被我干掉了 这里就不贴出来了 如果需要的话可以网上搜下 很好搜索的
失败原因是因为我这个界面是一个activity里四个fragment 里面有两个是这样的聊天室 都需要这种功能 但是监听是针对activity的所以会有冲突 导致的结果就是无论我怎么输入都是发送到第一个界面
2、我后边换的是最常用的方法 在
AndroidManifest.xml
对应的Activity里添加
android:windowSoftInputMode=”adjustPan”
或是android:windowSoftInputMode=”adjustResize”
属性这种完全没有效果 貌似是和我写的沉浸式状态栏冲突了
3、我又试了试在界面最外层布局包裹ScrollView
但是我们的目的是最上边的界面不被滑动 只把下边部分设置为滑动布局又会导致布局混乱 貌似ScrollView包裹的控件 位置属性貌似会失效
4、于是我又换了一个姿势去设置
//getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_ADJUST_PAN); getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_ADJUST_RESIZE);
这个有两种方式 一种布局会滑动一种会覆盖 滑动的直接跳过 覆盖的那个还是与我的沉浸式冲突 去掉沉浸式之后 结果是把底部的四个选择标识带着输入框一起顶起来了 这就。。。
如果只是这些的话我感觉我就该放弃了 苦搜无果只能去找大佬询问
获得秘籍+1
稍加修改 为我所用
editTextMessage是我的输入框id
mTaoLun是我需要滑动部分的布局id
messageListView2是我包裹发送+输入框的id
srollHeight + 125是因为这个本来不是为这种局面准备的 我写完后发现并没有全部顶起来 所以只加了一个暂时的值来控制高度 希望有大佬可以改动下这个值 变成一个随着手机变化自动变动的 貌似是需要获得布局未变化前messageListView2的高度坐标
editTextMessage.setOnFocusChangeListener(new View.OnFocusChangeListener() {
@Override
public void onFocusChange(View v, boolean hasFocus) {
controlKeyboardLayout(mTaoLun, messageListView2);
}
});
/**
* @param root 最外层布局,需要调整的布局
* @param scrollToView 被键盘遮挡的scrollToView,滚动root,使scrollToView在root可视区域的底部
*/
private void controlKeyboardLayout(final View root, final View scrollToView) {
root.getViewTreeObserver().addOnGlobalLayoutListener(
new ViewTreeObserver.OnGlobalLayoutListener() {
@Override
public void onGlobalLayout() {
Rect rect = new Rect();
// 获取root在窗体的可视区域
root.getWindowVisibleDisplayFrame(rect);
// 获取root在窗体的不可视区域高度(被其他View遮挡的区域高度)
int rootInvisibleHeight = root.getRootView().getHeight() - rect.bottom;
LogUtil.e("233", "不可视区域高度: " + rootInvisibleHeight);
// 若不可视区域高度大于100,则键盘显示 华为手机会有100多的默认区域高度 所以需要写大一点
if (rootInvisibleHeight > 200) {
int[] location = new int[2];
// 获取scrollToView在窗体的坐标
scrollToView.getLocationInWindow(location);
// 计算root滚动高度,使scrollToView在可见区域
int srollHeight = (location[1] + scrollToView.getHeight() + dp2px(10)) - rect.bottom;
LogUtil.e("233", "srollHeight: " + srollHeight);
//直播结束的弹窗会把这个值变为负数导致软件盘下去 所以加一个判断阻止
if (srollHeight >= 0) {
//布局抬高
root.scrollTo(0, srollHeight + 125);
}
} else {
// 键盘隐藏
//布局恢复
root.scrollTo(0, 0);
}
}
});
}
private int dp2px(int dpValue) {
final float scale = getResources().getDisplayMetrics().density;
return (int) (dpValue * scale + 0.5f);
}
搭嘎!(突然日语) 但是顶起来的效果是实现了 隐藏软键盘的效果却实现不了了 普通的方法要么崩溃要么没反应。。。 而且有个小bug就是弹起来时如果有什么弹出框之类的出现 输入框就会掉下去。。。我暂时还没解决这个 不过我觉得这个可以暂放。。。 已经修复(上边的代码已经修改)
隐藏软键盘的办法还是被我找到了
buttonSendMessage是发送按钮的id 点击这个id时隐藏软键盘 同一个activity不同fragment分别调用不会冲突哦
//隐藏软键盘
//点击其他部位隐藏软键盘 拦截该id的点击事件
buttonSendMessage.setOnTouchListener(new View.OnTouchListener() {
@Override
public boolean onTouch (View v, MotionEvent event){
InputMethodManager manager = (InputMethodManager) getActivity().getSystemService(Context.INPUT_METHOD_SERVICE);
if (event.getAction() == MotionEvent.ACTION_DOWN) {
if (getActivity().getCurrentFocus() != null && getActivity().getCurrentFocus().getWindowToken() != null) {
manager.hideSoftInputFromWindow(getActivity().getCurrentFocus().getWindowToken(), InputMethodManager.HIDE_NOT_ALWAYS);
}
}
return false;
}
});
写的不是很详细 但是对遇到同样需求的朋友应该会有帮助