zoukankan      html  css  js  c++  java
  • JS进阶 | 解决JQ keyup事件延迟的问题

    写在前面

      在使用keyup事件时,存在一个问题,假如想要做出类似于表单验证的demo:表单输入账号 “xxx” 后  再去ajax异步去后台数据库匹配,但是keyup事件的原理是每次键盘事件弹起就会检测,也就是输入“x”的时候就会检测,所以输入“xxx”就会使用三次ajax,这样的用户体验是不好的。再举一个例子,再用百度的时候,打开www.baidu.com 输入任意一个字符,就会自动弹出关于该字符的搜索信息,我感觉这个用户体验不好,我在输入一个字符的时候,百度搜索框下面某个新闻我很感兴趣,但是页面已经跳转,我history(-1)时,发现新闻页已经刷新了。这样我就看不到我想要看的新闻了。所以在输入“xxx”完整的字符再触发keyup事件显得比较重要。

    如何实现

      这个问题就是keyup事件延迟的问题。如何实现,很简单,就是使用定时器setTimeout和event.timeStamp。假设定期器为1000ms,定时器负责1000ms后触发keyup事件,setTimeout的原理就是,把当前事件的执行结果放入事件循环中,待JS引擎空闲时再去处理执行结果。event.timeStamp是一个事件的时间戳,表示发生事件的时间和日期(从 epoch 开始的毫秒数)epoch 是一个事件参考点。在这里,它是客户机启动的时间。

      在keyup事件中引用event.timeStamp,last = event.timeStamp 

      在定时器中进行判断 if(last==event.timeStamp) 为真 则执行ajax

      原理就是,last代表最后一次keyup的时间戳,你停止输入1000ms内没有再次触发keyup事件,则执行ajax,用代码表示就是(last==event.timeStamp)为真,如果你1000ms又触发了keyup事件,则继续判断,如果你停止输入1000ms内没有再次触发keyup事件,则执行ajax。

      用代码完成

      js: 

    // <input type="text" id="input">    
        $(function(){
            $("#input").focus();
            $("#input").on("keyup",function(e){
                $this = $(this);
                last = e.timeStamp;            
                setTimeout(function(){
                // console.log(e.timeStamp);
                var $data_data = $this.val();
                    if(last-e.timeStamp===0){
                        $.ajax({
                            type:"get",
                            url:"ajaxkeyup.php",
                            data:{
                                $data:$data_data
                            },
                            success:function(data){
                                console.log("ajax发送并接收响应成功显示的ok");
                                console.log(data);
    
                            },
                            onerror:function(){
                                console.log("not ok");
                            }
                        })
                    }
                },1000)
            })
        })

      php:

    <?php 
        $data = '123';
        $getData = $_GET['$data'];
        if ($getData==$data) {
            echo "后台检测匹配失败显示的ok";
        }else{
            echo "后台检测匹配失败显示的failed";
        }
     ?>

      模拟数据库的数据为“123”,完整输入“123”后 执行ajax

      demo如下

      有点不清晰,但是效果就是当输入"123"时 触发keyup事件,执行ajax,显示ajax发送并接收成功,后台服务器也返回成功

      当输入“1234”时,ajax发送并接收成功,但是后台检测失败

    总结

      这个问题是面试商汤科技呗问的问题,上一个被问的问题是promise实现红绿灯,这个问题是keyup事件的延迟。都使用了异步的操作方式,蚂蚁金服面试的时候也问JS有哪些异步操作,看来异步操作是JS的核心之一。

       分析JS异步操作

      定时器setTimeout与异步ajax同时执行,既有页面无刷新的魅力也有事件循环的感觉。爽。

      

      

      

      

      

      

  • 相关阅读:
    盛最多水的容器
    字符串的排序
    整数拆分
    TCP和UDP编程
    旋转图像
    非递减数列
    不同路径2
    不同路径
    压缩拉伸图片
    Java对List分割及使用Spring多线程调用
  • 原文地址:https://www.cnblogs.com/dirkhe/p/7457510.html
Copyright © 2011-2022 走看看