zoukankan      html  css  js  c++  java
  • 使用jsonp跨域调用百度js实现搜索框智能提示,并实现鼠标和键盘对弹出框里候选词的操作【附源码和在线测试地址】

    项目中常常用到搜索,特别是导航类的网站。自己做关键字搜索不太现实,直接调用百度的是最好的选择。
    使用jQuery.ajax的jsonp方法可以异域调用到百度的js并拿到返回值,当然$.getScript也可以实现跨域调用js。

    jsonp快速入门: 
    【原创】说说JSON和JSONP,也许你会豁然开朗,含jQuery用例 
    关于jquery.ajax的jsonp方法是用以及其error回调函数不能正确执行,请参考园长dudu的文章: 
    jquery ajax中使用jsonp的限制 
    jQuery插件jQuery-JSONP使用注意 
    其他有关jsonp的文章: 
    利用iframe实现ajax 跨域通信的解决方案

    ok,了解了jsonp的原理和应用后,我们看看百度的智能提示是如何做的
    在chrome的调试窗口下看看百度搜索发出的请求。当输入关键字“a”,请求如图:

    用firebug看下请求的参数,如图:



    请求方式:get请求
    请求参数:wd明显是要搜索的关键字;cb是请求回来的处理函数,名字可以随便给;t是时间戳,防止缓存的;p不知道什么意思,每次请求都给3就可以了;sid也不知道什么意思,不要也可以请求,如果想要也可以带上,值就是上面截图的值。

    请求地址和参数都知道了,于是写下如下js测试是否可以拿到关键字提示(源码里的test.html页面):

    var qsData = { 'wd': ‘a’, 'p': '3', 'cb': 'getData', 't': new Date().getMilliseconds().toString() };
         $.ajax({
              async: false,
              url: "http://suggestion.baidu.com/su",
              type: "GET",
              dataType: 'jsonp',
              jsonp: 'jsoncallback',
              data: qsData,
              timeout: 5000,
              success: function (json) {
              },
              error: function (xhr) {
              }
        });

    qsData封装所有请求要发送的参数;getData是自定义的名称,用于处理返回的关键字(以下示例代码把请求回来的关键字打印到了FireBug的控制台):

            function getData(data) {
                var Info = data['s'];  //获取异步数据
                console.log(Info);
            }

    监控下文本框,实时的发送ajax请求并拿回数据是这样的:

    ok,测试可用,的确可以拿到关键字提示。但是总不能把一堆关键字放到前台让用户看,至少得跟百度一样,可以用鼠标和键盘方向键从候选词框里选词吧。
    最关键的来了,现在开始写完整的智能提示并配合鼠标和键盘对候选词的操作(源码里的index.html页面),实现如下功能:

    1. 即时监控字母键和数字键,按下就发ajax请求(也可以设置延迟发请求,源码里有);同时监控空格、退格、Delete、Enter等键;
    2. 鼠标移入弹出层高亮选中的行,点击可上屏;
    3. 按键盘上下方向键可以选择候选词,回车提交跳转到百度搜索页面;
    4. 点击页面其他部位自动隐藏弹出框;
    5. 按ESC键隐藏弹出框

    监控鼠标和键盘输入的js(autoComplete.js 源码里有更详细的注释):

    var timeoutId;   //延迟请求服务器
    var highlightindex = -1;   //高亮标记
    $(function () {
        $("#searchText").keyup(function (event) {
            var myEvent = event || window.event;
            var keyCode = myEvent.keyCode;
            //console.log(keyCode);
    
            //监控键盘
            if (keyCode >= 65 && keyCode <= 90 || keyCode >= 48 && keyCode <= 57 || keyCode >= 96 && keyCode <= 111 || keyCode >= 186 && keyCode <= 222 || keyCode == 8 || keyCode == 46 || keyCode == 32 || keyCode == 13) {
                //延时操作
                //clearTimeout(timeoutId);
                //timeoutId = setTimeout(function () {
                //            timeoutId = FillUrls();
                //             }, 500)
                FillUrls();  //异步请求
                if (highlightindex != -1) {
                    highlightindex = -1;
                }
            }
            else if (keyCode == 38 || keyCode == 40) {
                if (keyCode == 38) {       //向上
                    var autoNodes = $("#auto").children("div")
                    if (highlightindex != -1) {
                        autoNodes.eq(highlightindex).css("background-color", "white");
                        highlightindex--;
                    } else {
                        highlightindex = autoNodes.length - 1;
                    }
                    if (highlightindex == -1) {
                        highlightindex = autoNodes.length - 1;
                    }
                    autoNodes.eq(highlightindex).css("background-color", "#ebebeb");
                    var comText = autoNodes.eq(highlightindex).text();
                    $("#searchText").val(comText);
                }
                if (keyCode == 40) {    //向下
                    var autoNodes = $("#auto").children("div")
                    if (highlightindex != -1) {
                        autoNodes.eq(highlightindex).css("background-color", "white");
                    }
                    highlightindex++;
                    if (highlightindex == autoNodes.length) {
                        highlightindex = 0;
                    }
                    autoNodes.eq(highlightindex).css("background-color", "#ebebeb");
                    var comText = autoNodes.eq(highlightindex).text();
                    $("#searchText").val(comText);
                }
            } else if (keyCode == 13) {     //回车
                if (highlightindex != -1) {
                    var comText = $("#auto").hide().children("div").eq(highlightindex).text();
                    highlightindex = -1;
                    $("#searchText").val(comText);
                } else {
                    $("#auto").hide();
                    $("#searchText").get(0).blur();
                }
            } else if (keyCode == 27) {    //按下Esc 隐藏弹出层
                if ($("#auto").is(":visible")) {
                    $("#auto").hide();
                }
            }
        });

     

    最后实现效果展示。可以鼠标选择候选词也可以键盘方向键选择,点击即可上屏,回车直接跳到百度页面:

    源码:点击下载

    在线演示地址:点击跳转

     
    摘自:http://blog.csdn.net/dyllove98/article/details/9674411

    百度检索框提示词条获取地址:

    http://suggestion.baidu.com/su?wd=word

    https://sp0.baidu.com/5a1Fazu8AA54nxGko9WTAnF6hhy/su?wd=word

  • 相关阅读:
    ACM ICPC 2008–2009 NEERC MSC A, B, C, G, L
    POJ 1088 滑雪 DP
    UVA 11584 最短回文串划分 DP
    POJ 2531 Network Saboteur DFS+剪枝
    UVa 10739 String to Palindrome 字符串dp
    UVa 11151 Longest Palindrome 字符串dp
    UVa 10154 Weights and Measures dp 降维
    UVa 10271 Chopsticks dp
    UVa 10617 Again Palindrome 字符串dp
    UVa 10651 Pebble Solitaire 状态压缩 dp
  • 原文地址:https://www.cnblogs.com/csniper/p/5536505.html
Copyright © 2011-2022 走看看