如何确定移动浏览器中的软键盘是否触发了调整大小事件

How to determine if a resize event was triggered by soft keyboard in mobile browser?

本文关键字:调整 小事件 大小事 是否 键盘 移动 何确定 浏览器      更新时间:2023-09-26

关于软键盘有很多讨论,但我还没有找到一个好的解决方案。

我有一个调整大小的功能,比如:

$(window).resize(function() {
    ///do stuff
});

我想在所有调整大小的事件上做该函数中的"东西",除非它是由软键盘触发的。如何确定软键盘是否触发了调整大小?

我最近遇到了一些问题,需要对此进行检查。我设法解决了这个问题:

$(window).on('resize', function(){
   // If the current active element is a text input, we can assume the soft keyboard is visible.
   if($(document.activeElement).attr('type') === 'text') {
      // Logic for while keyboard is shown
   } else {
      // Logic for while keyboard is hidden
   }
});

我只需要它用于文本输入,但很明显,它可以扩展到任何可能触发软键盘/数字选择器等的元素。

我刚刚修复了kirisu_kun的答案,使用prop()而不是attr():

$(window).on('resize', function(){
   // If the current active element is a text input, we can assume the soft keyboard is visible.
   if($(document.activeElement).prop('type') === 'text') {
      // Logic for while keyboard is shown
   } else {
      // Logic for while keyboard is hidden
   }
});

问题是,如果活动元素被聚焦,只需关闭键盘就可以触发调整大小事件,而不会改变焦点。。因此,键盘将被隐藏,但代码将进入焦点状态。

这个问题取决于是否有可靠的方法来检测屏幕键盘何时出现(或消失)在移动设备上。不幸的是,没有可靠的方法来检测这一点。类似的问题已经在SO上出现了好几次,并提出了各种技巧、窍门和解决方案(请参阅此答案以获取几个相关答案线程的链接)。

还要注意,当屏幕键盘出现时,调整大小事件并不总是触发的(请参阅此答案)。

我的一般建议是检测触摸屏的存在+检测活动元素是否属于触发屏幕键盘的类型(类似于这个答案)。然而,这种方法对于混合窗口设备(如Surface Pro)仍然会失败,因为有时屏幕键盘可能会出现在浏览器调整大小时,有时硬件键盘可能会在浏览器调整尺寸时使用。

我一直在寻找类似问题的解决方案。当url输入进入和退出视图时,我的调整大小事件被触发。这是我一直在做的事情…有可能的解决方案吗?

因此,基本上,你只需检查屏幕宽度是否单独发生了变化,如果不同,只在调整大小时启动你的功能:

例如:

var saveWindowWidth = true;
    var savedWindowWidth;
//set the initial window width
    if (saveWindowWidth = true){
        savedWindowWidth = windowWidth;
        saveWindowWidth = false;
    }

//then on resize...

$(window).resize(function() {
//if the screen has resized then the window width variable will update
        windowWidth = window.innerWidth;

//if the saved window width is still equal to the current window width do nothing
        if (savedWindowWidth == windowWidth){
            return;
        }

//if saved window width not equal to the current window width do something
        if(savedWindowWidth != windowWidth) {
           // do something
            savedWindowWidth = windowWidth;
        }
    });

关于,您需要集中注意以下几点

  1. 所有的软键盘只影响高度而不影响宽度
  2. 焦点元素标签可以是输入或文本区域
  3. 当元素聚焦时,高度将减小(或)当焦点向外时,高度会增加

当浏览器调整大小时,您可以使用这些组合

function getWidth(){
return $( window ).width();
}
function getHeight(){
return $( window ).height();
}
function isFocus(){
return $(document.activeElement).prop('tagName')=='INPUT' || $(document.activeElement).prop('tagName')=='TEXTAREA';
}
var focused = false;
var windowWidth=getWidth(),windowHeight=getHeight();
//then on resize...    
$(window).resize(function() {
var tWidth=getWidth(),tHeight=getHeight(),tfocused=isFocus();
//if the saved window width is still equal to the current window width do nothing
if (windowWidth == tWidth && ((tHeight < windowHeight && !focused && tfocused) || (tHeight > windowHeight && focused && !tfocused))){
 windowWidth=tWidth;
 windowHeight=tHeight;
 focused=tfocused;
 return;
}
else{
 windowWidth=tWidth;
 windowHeight=tHeight;
 focused=tfocused;
 //Your Code Here
}
});

与前面的答案类似,但针对所有类型的有焦点的表单(显然,如果没有form父级,则会在输入时失败)

$(window).resize(function() {
    if($('form *').focus()) {
        alert('ignore this');
    } else {
        // do the thing
    }
});

所以也许这个。。。

$(window).resize(function() {
    if($('input, select, etc').focus()) {
        alert('ignore this');
    } else {
        // do the thing
    }
});

在当前版本的chrome webview中运行良好。我刚刚使用下面的代码在Angular中实现了窗口大小调整功能。

@HostListener('window:resize', ['$event'])
  onResize(event) {
  // Do you handling here.
}

注意:使用也可以实现同样的效果

 window.addEventListener('resize', () => {
   // Do handling here
 });