解决position:fixed受虚拟键盘的影响
1. 不适用fixed定位,使用替代方案(推荐的方法):
a方案:使用overflow-y:scroll;+position:absolute;
b方案:使用overflow-y:scroll;+flex布局;
其中,a方案内容区域的高度通过js控制;b方案内容区域的高度通过flex布局自动排版;
2. 根据输入框获取焦点与失去焦点事件切换fixed定位与static定位
问题源头可能是:移动端虚拟键盘出现的条件是:文本框(文本类)获得焦点
弹出键盘后原先定位与底部的东西会被虚拟键盘顶上去,样式错乱!
首先我们会想到监听focus和blur事件,但是会有bug,虚拟键盘有自带的收起键盘,这样输入框还是聚焦事件,并没有触发blur事件。所以会导致失效的。
解决办法
我们可以换一个思路。监听改变浏览器窗口高度的时候去触发事件。1
2
3
4
5
6
7
8windowInnerHeight = window.innerHeight; //获取当前浏览器窗口高度
$(window).resize(function(){
if(window.innerHeight < windowInnerHeight){
$('.footer').removeClass('footerss');
}else{
$('.footer').addClass('footerss');
}
});
解决输入框input获取焦点得时,虚拟键盘会把fixed元素顶上去(次现在在部分安卓上能发现)
1 | $('#phone').bind('focus',function(){ |
解决屏幕旋转也会出现以上问题
1 | $(document).bind('orientationchange',function(){ |
通过resize() 方法触发 resize 事件,或规定当发生 resize 事件时运行的函数。
1 |
|
h5 ios中软键盘弹起后 fixed定位失效
position: fixed;在ios手机中会存在一个失效情况:
如果页面有输入框存在,点击输入框软键盘弹起后会发生一个现象:
- 针对当前内容高度小于屏幕高度时:
上下滑动页面时候,发现之前fixed定位在顶部的元素会跟随页面滚动,变成了absolute定位的效果。 - 针对当前内容高度大于屏幕高度时:
之前fixed定位在顶部的View不见了,下滑往上翻页面后,就会看那个fixed定位的元素错落在页面中,但并不是在最顶部。
综上可以看出,ios浏览器是针对fixed定位的元素作了处理,不再是之前定位效果,变成了absolute定位的效果但并不是absolute,但可以理解为top:对应为当前body的scrollTop值。
那么该怎么解决这个问题呢?
在这里我是比较倾向于遵循ios浏览器处理fixed元素的初衷,浏览器去处理fixed元素应该是有它考虑的地方,退一步说其实也没有必要在这个情况下强制显示顶部元素,这时候用户的重点在于输入。
这里给出的方案就是:在软键盘弹起后,直接把fixed的元素变成absolute的,不需要浏览器自己去做处理,待键盘收起后再恢复成fixed。
1 | //以下代码环境是在React中 |
h5 安卓 键盘弹起界面适配 修改webview高度
存在按钮使用绝对定位去实现。然后再到真机上去测试时,会发现ios手机是蛮正常的体验,软键盘会直接从底部覆盖最下面的按钮的,那是因为ios上的键盘是处在窗口的最上层,直接覆盖窗口不会挤压窗口;
首先还是从源头上看,针对安卓系统来说,软键盘弹起的方式是很有多种的常用的是这2种android:windowSoftInputMode=”adjustPan|adjustResize”
- “adjustResize”
该Activity主窗口总是被调整屏幕的大小以便留出软键盘的空间,会调用onSizeChanged方法 - “adjustPan”
该Activity主窗口并不调整屏幕的大小以便留出软键盘的空间。相反,当前窗口的内容将自动移动以便当前焦点 不被键盘覆盖和用户能总是看到输入内容的部分。不会调用onSizeChanged方法
综上所述安卓会发生这个现象是因为原窗口为了留出软键盘的空间,高度发生了改变,绝对定位在底部的按钮就会被挤压,给人的假象就是被键盘顶起。既然我们知道了原因出在了原窗口高度发生了改变,那就有可做文章的地方,请看下面的代码:
1 | //获取原窗口的高度 |
h5 移动端 监听软键盘弹起、收起
在adnroid中如何监听软键盘的弹起与收起,是利用的窗口的高度发生变化
window.onresize事件来做突破点的,但是ios中软键盘的弹起收起并不触发window.onresize事件。
- 总结:
- 在ios中软键盘弹起时,仅会引起$(‘body’).scrollTop值改变,但是我们可以通过输入框的获取焦点情况来做判断,但也只能在ios中采用这个方案,因为在android中存在主动收起键盘后,但输入框并没有失焦,而ios中键盘收起后就会失焦;
- 在android中软键盘弹起或收起时,会改变window的高度,因此监听window的onresize事件;
1 | //一、Android |
使用fiexd定位input框可以被在ios系统中唤起键盘跟着推上去
当键盘出来的时候,红色的div不见了。然后我就查了一下,是ios里面的就有这个bug。我就试了很多网上的方法都是不行。发现只有ios这样,安卓没有。我就做了个兼容判断
1 | //评论输入框 |
1 | mounted () { |
今天这个bug 遇到了新问题,同样的华为手机上,当从别的路由吊起输入键盘的时候回到当前路由,
document.documentElement.clientHeight就变成了减去输入键盘高度的值,
这时需要在页面第一次加载将document.documentElement.clientHeight记录到store中,store中的值不会因为页面重新渲染而改变。

