1。问题描述在app中打开H5页面,页面包含一个input输入框,点击input调出软键盘,输入完成后点击下方提交按钮弹出toast,出现一个现象吐司的跳动,如下面的动画所示。其中:toast采用position:fixed进行固定定位2.关于position:fixed的分析原因首先看MDN对position:fixed的描述:不为元素预留空间,而是指定元素相对于屏幕视口(viewport)指定元素位置。滚动屏幕时元素的位置不会改变。注意position:fixed是相对于屏幕视口(viewport)的位置定位的。那么toast是不是因为viewport的变化而跳动了呢?关于viewportMDN中viewport的描述:@viewport规则允许我们设置文档视口的大小。此功能主要用于移动设备。当按百分比计算尺寸时,它是指初始视口(viewport)。初始视口是任何用户代理和样式修改它之前的视口。如果桌面浏览器不处于全屏模式,则它们通常基于窗口大小。在移动设备上(或桌面浏览器的全屏模式),初始视口通常是应用程序可用的屏幕部分。它可能是全屏或减去操作系统或其他应用程序占用的部分(例如状态栏)。我们注意到视口会随着操作系统或应用程序的占用而改变。激活软键盘时视口是否发生变化?验证猜测js提供了Window.innerHeight方法来获取浏览器窗口的视口高度。经验证,激活软键盘后,viewport确实发生了变化。此时视口的高度就是我们看到的可见屏幕的高度——键盘的高度,所以我们看到的toast跳转是视口变化引起的。3、解决方法是用绝对定位position:absolute代替position:fixed。通常toast直接插在body元素下面(当然也可以是其他任何元素),即toast是body元素的直接子元素。因此,toast可以设置相对于body元素的绝对定位。代码如下:body{position:relative;}.toast{//固定屏幕中间position:absolute;顶部:50%;左:50%;变换:translate3d(-50%,-50%,0);}4。注意事项在使用position:fixed替换成position:absolute的方案时,如果top和left设置了百分比,需要注意设置absolute定位元素的offsetParent的高宽值。因为绝对定位是相对于position属性值不是static的父元素(即offsetParent),top和left的设置百分比是根据offsetParent的高和宽计算的。例如,在上面动画中的示例中,您可以看到body的内容高度远远小于屏幕的高度。因此,如果你想让toast在屏幕上居中,你需要为body元素设置一个合理的高度(通过设置min-height或height)。上面例子的完整代码:html{height:100%;//设置html为浏览器窗口的高度(如果不设置100%,则html的高度等于body的高度)}body{position:relative;最小高度:600px;//设置最小高度}.toast{//固定屏幕中间position:absolute;顶部:50%;左:50%;transform:translate3d(-50%,-50%,0);}offsetParent概念补充了HTMLElement。offsetParent只读属性返回对最近(在包含层次结构中最近)定位的包含元素的对象的引用。如果元素是非定位的,则返回最近的td、th、table或body。5.总结针对position:fixedshifting在移动端调用软键盘引起的问题,可以使用绝对定位(position:absolute)代替固定定位(position:fixed)来救国。如果给top和left设置了百分比,还需要注意为绝对定位的元素设置offsetParent的高宽值。
