看来,唯一的解决方案可能是停止在背景帧上捕获touchstart事件.我喜欢像透明div这样的解决方案来捕获事件作为中介,但我还没有得到这样的工作.是否有其他解决方法?
<!DOCTYPE html> <html> <head> <style type='text/css'> iframe { position:absolute; } #background { border: solid 3px red; z-index:1; width: 20em; height: 20em; } #foreground,#foreground2 { border: solid 2px yellow; z-index:2; top: 15em; height: 5em; } #foreground2 { top: 22em; } </style> <script type='text/javascript'> window.onload=function(){ document.getElementById("foreground").contentDocument.write("<input type='text' value='text'/><input type='text'/>"); document.getElementById("foreground2").contentDocument.write("<input type='text' value='text'/><input type='text'/>"); document.getElementById("background").addEventListener("touchstart",function() { console.log("touch"); }); } </script> </head> <body> <iframe id=background></iframe> <iframe id=foreground></iframe> <iframe id=foreground2></iframe> </body> </html>
解决方法
经过一些测试,我可以确认它总是出现在下列情况下:
>当使用iframe / object / embed HTML标签将HTML内容与javascript触摸事件绑定(touchstart / touchend等)组合在HTML内容中的元素上时.一旦用户再次触摸iframe / object / embed标签内的输入元素(有时候更多),则他通过屏幕键盘输入的所有内容在输入字段内不再出现. (有趣的是,键盘上方的单词建议仍然对用户键入的所有内容都做出反应,它不再出现在输入字段中).有时可以通过输入字段中的退格键删除内容,但不添加任何内容.
以下变体似乎存在:
>触摸事件直接绑定在输入元素上,导致此错误.
>触摸事件绑定在父元素上,其中包含输入元素(不必是直接的子代).
>输入元素在视觉上位于具有触摸事件绑定的元素之上. DOM内部的这个元素是什么,或者触摸边界元素和输入字段之间是否有覆盖元素.触摸绑定元素也不一定是可见的,因为这样会发生(就像其他元素在它上面一样).一旦用户触摸了触摸界限元素后面的输入区域,就会出现错误.这是有趣的,因为如果输入元素仅部分覆盖触摸限制元素,触摸触摸元素不在后面的输入部分将不会导致此错误.
解决方案:
首先:如果您在touch bound元素上实验了preventDefault / stopPropagation和其他类似的东西,那似乎并没有什么帮助.绑定元素上的事件/触摸绑定会发生什么事情(我测试过,当出现错误时不会被调用/触发).即使CSS解决方案,如“指针事件:无”触摸绑定元素也没有帮助.所以以下解决方案是我们迄今唯一的希望:
>动态地绑定触摸事件,如这个线程中建议的,所以你只有当你真正需要它们时才激活,而不是删除它们,以防止上面写的所有3种情况.>当输入元素在前面时,移动具有触摸事件绑定的元素或容器.使用CSS变换等就可以,甚至只是在视觉上将它们从输入字段中移出. (见上面的bug变体3).所以取决于你的布局,例如如果您有一个侧边栏,其中包含从页面侧面移动并覆盖主要内容的搜索字段,请考虑不覆盖主要内容,而将其移动到侧边.>在不使用触摸事件绑定的元素上使用’display:none’.这是唯一的css属性,似乎解决了bug变体3.“可见性:隐藏”在我的测试中没有影响.具有’display:none’的元素不再影响到这个错误的输入元素.如果您正在构建一个寻呼机,那么您应该考虑设置页面或“触摸绑定元素”,这些设置页面或视图不显示.这将防止错误变体3.>当然,最好的事情是避免使用iframe / object / embed标签来显示其他内容,只要这个bug存在.