트위터 부트 스트랩 typeahead 아약스 예제


280

드롭 다운을 채우기 위해 아약스 호출을 하는 Twitter 부트 스트랩 typeahead 요소 의 작동 예제를 찾으려고합니다 .

기존 작업 jquery 자동 완성 예제가 있는데 Ajax URL을 정의하고 응답을 처리하는 방법

<script type="text/javascript">
//<![CDATA[
$(document).ready(function() {
    var options = { minChars:3, max:20 };
    $("#runnerquery").autocomplete('./index/runnerfilter/format/html',options).result(
            function(event, data, formatted)
                {
                    window.location = "./runner/index/id/"+data[1];
                }
            );
       ..

이것을 typeahead 예제로 변환하려면 무엇을 변경해야합니까?

<script type="text/javascript">
//<![CDATA[
$(document).ready(function() {
    var options = { source:'/index/runnerfilter/format/html', items:5 };
    $("#runnerquery").typeahead(options).result(
            function(event, data, formatted)
                {
                    window.location = "./runner/index/id/"+data[1];
                }
            );
       ..

' typeahead에 대한 원격 소스 지원 추가 '문제가 해결 될 때까지 기다립니다 .


좀 더 구체적으로 말하면 자동 완성 옵션과 결과 처리 기능이 텍스트 미리 옵션에 어떻게 매핑되는지 궁금합니다. 재정의 될 수있는 정의 된 textalert 결과 처리 함수 세트가 있습니까, 아니면 기본 jquery api에서 상속 된 메소드 이름입니다.
emeraldjava

1
지금 Stijn Van Bael의 답변을 정답으로 표시 할 수 있습니까? bogert의 답변은 오래된 버전의 Bootstrap에서만 작동합니다.
Giles Roberts

답변:


302

편집 : typeahead가 더 이상 Bootstrap 3에 번들로 제공되지 않습니다.

Bootstrap 2.1.0부터 2.3.2까지 다음과 같이 할 수 있습니다.

$('.typeahead').typeahead({
    source: function (query, process) {
        return $.get('/typeahead', { query: query }, function (data) {
            return process(data.options);
        });
    }
});

다음과 같이 JSON 데이터를 사용하려면

{
    "options": [
        "Option 1",
        "Option 2",
        "Option 3",
        "Option 4",
        "Option 5"
    ]
}

jQuery가 JSON으로 인식하도록 JSON 데이터는 올바른 MIME 유형 (application / json)이어야합니다.


3
Typeahead 포크에서와 같이 데이터는 JSON 배열의 문자열이어야하고 컨텐츠 유형은 application / json이어야합니다.
Stijn Van Bael

9
2.1은 문자열 배열이 아닌 json을 사용할 수 있습니까? 사용자에게 가치를 부여하고 추가 처리를 위해 ID를 사용해야합니다. 커스텀 포크를 픽업하지 않고도 가능합니까?
Anton

2
@Stijin 표시된 옵션의 id를 처리하기 위해 익명 함수가 어떻게 사용되는지에 대한 예가 있습니까? 감사!
Acyra

1
이 방법을 사용 하면 입력의 모든 키 입력에 대해 AJAX가 작성된다는 것을 지적하고 싶습니다 . 서버가 본질적으로 정적 데이터를 반환하는 경우 (즉, 실제로 쿼리와 관련이없는 작업) 상당히 낭비가 될 수 있습니다.
Dologan

2
get대신에 사용 getJSON합니까? 더 적절한 것 같습니다.
greg0ire

119

Ajax 호출을 지원 하는 BS Typeahead 포크 를 사용할 수 있습니다 . 그러면 다음과 같이 쓸 수 있습니다 :

$('.typeahead').typeahead({
    source: function (typeahead, query) {
        return $.get('/typeahead', { query: query }, function (data) {
            return typeahead.process(data);
        });
    }
});

1
POST 데이터의 반환 유형에 대한 jQuery의 "지능형 추측"은 예를 들어을 반환했을 때 작동하지 않았습니다 ["aardvark", "apple"]. 호출 에서 dataType매개 변수 를 명시 적으로 설정해야했습니다 $.post. jQuery.post ()를 참조하십시오 .
Rusty Fausak

1
@rfausak 또는 Content-type헤더를application/json
Rusty Fausak

23
Uncaught TypeError가 발생했습니다 : undefined의 'toLowerCase'메서드를 호출 할 수 없습니다.
Krishnaprasad Varma

보낸 링크에서 source함수를 실행할 수조차 없습니다 .
James

8
좋은 대답입니다! REST 표준을 충족시키기 위해 대신 GET 요청을 사용합니다.
Mauro

72

부트 스트랩 2.1.0에서 시작 :

HTML :

<input type='text' class='ajax-typeahead' data-link='your-json-link' />

자바 스크립트 :

$('.ajax-typeahead').typeahead({
    source: function(query, process) {
        return $.ajax({
            url: $(this)[0].$element[0].dataset.link,
            type: 'get',
            data: {query: query},
            dataType: 'json',
            success: function(json) {
                return typeof json.options == 'undefined' ? false : process(json.options);
            }
        });
    }
});

이제 HTML 코드에 "json-request"링크를 배치하여 통합 코드를 만들 수 있습니다.


11
하지만 사용하도록 변경합니다 $(this)[0].$element.data('link').
Andrew Ellis

또는this.$element.data('link')
Richard87

51

모든 응답은 BootStrap 3에 더 이상 존재하지 않는 BootStrap 2 자동 완성을 참조합니다.

여기에서 새로운 post-Bootstrap Twitter typeahead.js 를 사용하여 AJAX 예제를 찾는 다른 사람들을 위해 여기에 실제 예제가 있습니다. 구문은 약간 다릅니다.

$('#mytextquery').typeahead({
  hint: true,
  highlight: true,
  minLength: 1
},
{
  limit: 12,
  async: true,
  source: function (query, processSync, processAsync) {
    processSync(['This suggestion appears immediately', 'This one too']);
    return $.ajax({
      url: "/ajax/myfilter.php", 
      type: 'GET',
      data: {query: query},
      dataType: 'json',
      success: function (json) {
        // in this example, json is simply an array of strings
        return processAsync(json);
      }
    });
  }
});

이 예제에서는 동기식 ( processSync 호출 )과 비동기식 제안 을 모두 사용 하므로 일부 옵션이 즉시 표시되고 다른 옵션이 추가됩니다. 하나만 사용할 수 있습니다.

문자열이 아닌 객체로 작업하는 것을 포함하여 많은 바인딩 가능한 이벤트와 일부 강력한 옵션이 있습니다.이 경우 고유 한 사용자 지정 표시 기능을 사용하여 항목을 텍스트로 렌더링합니다.


1
감사합니다. 질문 하나 더 : processAsync에서 "TypeError : suggests.slice는 함수가 아닙니다."라는 메시지가 나타납니다. 반환 된 JSON은 어떻게 생겼습니까? 가장 좋은 추측은 다음과 같습니다. {: suggestions => [ "사물 1", "사물 2", "사물 3"]}
user1515295

1
유효한 JSON 문자열을 반환하십시오. AJAX 제안 함수는 문자열 배열 (예 : ["Thing 1","Thing 2"]사용자 정의 표시 기능)을 사용하여 필요에 따라 개체 배열을 [{"id":1,"label":"Foo"},{"id":2,"label":"Bar"}]
반환

을 반환합니다 [{"id":1,"label":"Foo"},{"id":2,"label":"Bar"}]. 이제 id와 label을 사용하여 두 개의 열을 자동 완성 드롭 다운에 표시하려고합니다. 어떻게해야합니까?
Vishal

2
나의 하나님 !!! 지난 3 일 동안 아무도 언급하지 않았습니다. 지금까지 동기화 기능으로 테스트하고있었습니다. 고마워 친구!!
Gilson PJ

감사 ! 부트 스트랩 4.3 및 jquery 3.4에서 잘 작동합니다. 그러나 마우스를 가져 가면 나열된 옵션이 강조 표시되지 않습니다. 나는 그것이 자동 완성 기능의 일부라고 생각했습니다.
Binita Bharati '10

25

아약스 기능을 갖춘 독창적 인 Typeahead Bootstrap 플러그인을 강화했습니다. 사용하기 매우 쉬운 :

$("#ajax-typeahead").typeahead({
     ajax: "/path/to/source"
});

여기 github 저장소가 있습니다 : Ajax-Typeahead


Gudbergur의 코드를 살펴 보았습니다. 솔직히, 나는 이것을 가장 좋아했습니다. 좀 더 친숙하고 더 많은 기능을 제공합니다. 잘 했어 폴! 내가 제안 할 것은 README에서 사용자가 코드를 올바르게 사용하려면 JSON 데이터를 JS로 구문 분석해야한다는 것을 상기시키는 것입니다. 나는 당신이 나를 위해 그것을 파싱하고 있다고 생각했습니다. 그렇지 않으면 꽤 좋습니다, 감사합니다! :)
Bane

3
서버는 JSON 객체 대신 문자열을 반환합니다. jQuery의 $ .ajax ()는 호출에 사용되며 구문 분석을 처리합니다.
Paul Warelis

1
절대적으로 맞습니다, 캐치 주셔서 감사합니다! :)이 플러그인은 매우 잘 작동합니다.
베인

안녕하세요, 서버 쪽은 JSON어떻게 생겼습니까? 나는 받고있다 Uncaught TypeError: Cannot read property 'length' of undefined . json_encode($array)올바른 헤더 ( 'Content-Type: application/json; charset=utf-8')를 사용 하고 보내고 있습니다 . jquery 버전jQuery v1.9.1
Kyslik

5

jquery-ui.min.js에서 일부 수정을 수행했습니다.

//Line 319 ORIG:
this.menu=d("<ul></ul>").addClass("ui-autocomplete").appendTo(d(...
// NEW:
this.menu=d("<ul></ul>").addClass("ui-autocomplete").addClass("typeahead").addClass("dropdown-menu").appendTo(d(...

// Line 328 ORIG:
this.element.addClass("ui-menu ui-widget ui-widget-content ui-corner-all").attr...
// NEW:this.element.attr....

// Line 329 ORIG:
this.active=a.eq(0).children("a")
this.active.children("a")
// NEW:
this.active=a.eq(0).addClass("active").children("a")
this.active.removeClass("active").children("a")`

다음 CSS를 추가하십시오.

.dropdown-menu {
    max-width: 920px;
}
.ui-menu-item {
    cursor: pointer;        
}

완벽하게 작동합니다.


어떤 버전의 jquery ui min을 사용하고 있습니까?
emeraldjava

jQuery 1.7.1 및 jQuery UI 1.8.16에 이것이 필요한 경우 jQuery UI 파일을 변경하는 위치를 보여주는 위 수정 사항을 기반으로 GIST를 만들었습니다. gist.github.com/1884819 - 라인 // 주석으로 수정
리처드 홀리스에게

이것은 매우 오래된 질문 / 답변이지만 타사 구성 요소 코드를 변경하는 것은 항상 나쁜 습관이라고 말하고 싶습니다. 업그레이드 할 때마다 모든 변경 사항을 다시 방문해야합니다. 이 특별한 경우, jQuery 위젯을 상속하여 사용자 정의하는 것이 훨씬 안전한 방법입니다. 따라서 기본적으로 자신의 위젯을 만들고 핵심 위젯 (이 경우 자동 완성)에서 상속하고 상상력을 발휘하십시오! :)
AlexCode

3

이 방법을 사용하고 있습니다

$('.typeahead').typeahead({
    hint: true,
    highlight: true,
    minLength: 1
},
    {
    name: 'options',
    displayKey: 'value',
    source: function (query, process) {
        return $.get('/weather/searchCity/?q=%QUERY', { query: query }, function (data) {
            var matches = [];
            $.each(data, function(i, str) {
                matches.push({ value: str });
            });
            return process(matches);

        },'json');
    }
});

답변에 설명을 추가 할 수 있다면 좋을 것입니다. 예를 들어, 기존 답변에 제시된 솔루션과 솔루션의 차이점은 무엇입니까?
honk

2

부트 스트랩을 사용하여 전화를 걸 수 있습니다. 현재 버전에 소스 업데이트 문제가 없습니다. post response로 부트 스트랩의 typeahead 데이터 소스를 업데이트하는 데 문제가 있습니다 . 즉, 일단 업데이트 된 부트 스트랩 소스를 다시 수정할 수 있습니다.

예를 들어 아래를 참조하십시오.

jQuery('#help').typeahead({
    source : function(query, process) {
        jQuery.ajax({
            url : "urltobefetched",
            type : 'GET',
            data : {
                "query" : query
            },
            dataType : 'json',
            success : function(json) {
                process(json);
            }
        });
    },
    minLength : 1,
});

2

허용되는 답변의 커피 스크립트 버전을 찾는 사람들에게 :

$(".typeahead").typeahead source: (query, process) ->
  $.get "/typeahead",
    query: query
  , (data) ->
    process data.options

2

나는이 게시물을 겪었고 모든 것이 올바르게 작동하고 싶지 않았고 결국 몇 가지 답변으로 비트를 함께 조각했기 때문에 100 % 작동하는 데모를 가지고 참조 용으로 여기에 붙여 넣습니다.이를 PHP 파일에 붙여 넣고 포함되어 있는지 확인하십시오 올바른 장소.

<?php if (isset($_GET['typeahead'])){
    die(json_encode(array('options' => array('like','spike','dike','ikelalcdass'))));
}
?>
<link href="bootstrap.css" rel="stylesheet">
<input type="text" class='typeahead'>
<script src="jquery-1.10.2.js"></script>
<script src="bootstrap.min.js"></script>
<script>
$('.typeahead').typeahead({
    source: function (query, process) {
        return $.get('index.php?typeahead', { query: query }, function (data) {
            return process(JSON.parse(data).options);
        });
    }
});
</script>

2

서비스가 올바른 애플리케이션 / json 컨텐츠 유형 헤더를 리턴하지 않는 경우이를 시도하십시오.

$('.typeahead').typeahead({
    source: function (query, process) {
        return $.get('/typeahead', { query: query }, function (data) {
            var json = JSON.parse(data); // string to json
            return process(json.options);
        });
    }
});

1

업데이트 : 포크를 사용하여 코드를 수정했습니다.

또한 $ .each 대신 Tomislav Markovski가 제안한대로 $ .map으로 변경했습니다.

$('#manufacturer').typeahead({
    source: function(typeahead, query){
        $.ajax({
            url: window.location.origin+"/bows/get_manufacturers.json",
            type: "POST",
            data: "",
            dataType: "JSON",
            async: false,
            success: function(results){
                var manufacturers = new Array;
                $.map(results.data.manufacturers, function(data, item){
                    var group;
                    group = {
                        manufacturer_id: data.Manufacturer.id,
                        manufacturer: data.Manufacturer.manufacturer
                    };
                    manufacturers.push(group);
                });
                typeahead.process(manufacturers);
            }
        });
    },
    property: 'name',
    items:11,
    onselect: function (obj) {

    }
});

그러나 나는 얻는 것에 의해 약간의 문제에 직면하고있다

잡히지 않은 TypeError : 정의되지 않은 'toLowerCase'메서드를 호출 할 수 없습니다

최신 게시물에서 볼 수 있듯이 여기에서 알아 내려고 노력 중입니다 .

이 업데이트가 도움이 되길 바랍니다.


OP와 관련이 없음 : Array.map대신 사용 $.each하고 전체 success콜백 함수 의 내용을var manufacturers = results.data.manufacturers.map(function (item) { return { id: item.Manufacturer.id, manufacturer: item.Manufacturer.manufacturer } });
Tomislav Markovski로

감사합니다 @TomislavMarkovski 제안한대로 코드를 수정했습니다.
mmoscosa 2016 년

0

나는 당신을위한 실제 사례가 없거나 매우 깨끗한 해결책을 가지고 있지 않지만 내가 찾은 것을 말해 줄 것입니다.

TypeAhead의 자바 스크립트 코드를 보면 다음과 같습니다.

items = $.grep(this.source, function (item) {
    if (that.matcher(item)) return item
  })

이 코드는 jQuery "grep"메소드를 사용하여 소스 배열의 요소를 일치시킵니다. AJAX 호출에 연결할 수있는 곳이 없었으므로 이에 대한 "깨끗한"해결책은 없습니다.

그러나 이것을 수행하는 다소 해킹 된 방법은 grep 메소드가 jQuery에서 작동하는 방식을 이용하는 것입니다. grep의 첫 번째 인수는 소스 배열이고 두 번째 인수는 소스 배열과 일치하는 데 사용되는 함수입니다 (부트 스트랩은 초기화 할 때 제공 한 "matcher"를 호출합니다). 당신이 할 수있는 일은 소스를 더미 단일 요소 배열로 설정하고 AJAX 호출을 사용하여 매처를 함수로 정의하는 것입니다. 그렇게하면 AJAX 호출이 한 번만 실행됩니다 (소스 배열에는 하나의 요소 만 있기 때문에).

이 솔루션은 해킹뿐만 아니라 TypeAhead 코드가 모든 키 누름을 조회하도록 설계 되었기 때문에 성능 문제가 발생합니다 (AJAX 호출은 매번 키를 누를 때마다 또는 특정 유휴 시간 후에 만 ​​발생해야 함). 내 조언은 시도해 보는 것이지만 다른 자동 완성 라이브러리를 사용하거나 문제가 발생하면 AJAX 이외의 상황에서만 사용하십시오.


0

ajax를 사용할 때 올바른 결과 표시에 문제가있는 경우 $.getJSON()대신 시도 $.get()하십시오.

필자의 경우 서버 측을 $.get()사용했지만을 사용할 때 모든 결과의 첫 문자 만 얻었습니다 json_encode().


0

나는 $().one() 이것을 해결하기 위해 사용 한다. 페이지가로드되면 서버에 아약스를 보내고 완료를 기다립니다. 그런 다음 결과를 함수에 전달하십시오. $().one()force typehead.js 가 입력에 한 번만 첨부하기 때문에 중요 합니다. 글을 잘못 써서 죄송합니다.

(($) => {
    
    var substringMatcher = function(strs) {
        return function findMatches(q, cb) {
          var matches, substringRegex;
          // an array that will be populated with substring matches
          matches = [];
      
          // regex used to determine if a string contains the substring `q`
          substrRegex = new RegExp(q, 'i');
      
          // iterate through the pool of strings and for any string that
          // contains the substring `q`, add it to the `matches` array
          $.each(strs, function(i, str) {
            if (substrRegex.test(str)) {
              matches.push(str);
            }
          });
          cb(matches);
        };
      };
      
      var states = [];
      $.ajax({
          url: 'https://baconipsum.com/api/?type=meat-and-filler',
          type: 'get'
      }).done(function(data) {
        $('.typeahead').one().typeahead({
            hint: true,
            highlight: true,
            minLength: 1
          },
          {
            name: 'states',
            source: substringMatcher(data)
          });
      })
      

})(jQuery);
.tt-query, /* UPDATE: newer versions use tt-input instead of tt-query */
.tt-hint {
    width: 396px;
    height: 30px;
    padding: 8px 12px;
    font-size: 24px;
    line-height: 30px;
    border: 2px solid #ccc;
    border-radius: 8px;
    outline: none;
}

.tt-query { /* UPDATE: newer versions use tt-input instead of tt-query */
    box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);
}

.tt-hint {
    color: #999;
}

.tt-menu { /* UPDATE: newer versions use tt-menu instead of tt-dropdown-menu */
    width: 422px;
    margin-top: 12px;
    padding: 8px 0;
    background-color: #fff;
    border: 1px solid #ccc;
    border: 1px solid rgba(0, 0, 0, 0.2);
    border-radius: 8px;
    box-shadow: 0 5px 10px rgba(0,0,0,.2);
}

.tt-suggestion {
    padding: 3px 20px;
    font-size: 18px;
    line-height: 24px;
    cursor: pointer;
}

.tt-suggestion:hover {
    color: #f0f0f0;
    background-color: #0097cf;
}

.tt-suggestion p {
    margin: 0;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script src="https://twitter.github.io/typeahead.js/releases/latest/typeahead.bundle.js"></script>

<input class="typeahead" type="text" placeholder="where ?">


-1
 $('#runnerquery').typeahead({
        source: function (query, result) {
            $.ajax({
                url: "db.php",
                data: 'query=' + query,            
                dataType: "json",
                type: "POST",
                success: function (data) {
                    result($.map(data, function (item) {
                        return item;
                    }));
                }
            });
        },
        updater: function (item) {
        //selectedState = map[item].stateCode;

       // Here u can obtain the selected suggestion from the list


        alert(item);
            }

    }); 

 //Db.php file
<?php       
$keyword = strval($_POST['query']);
$search_param = "{$keyword}%";
$conn =new mysqli('localhost', 'root', '' , 'TableName');

$sql = $conn->prepare("SELECT * FROM TableName WHERE name LIKE ?");
$sql->bind_param("s",$search_param);            
$sql->execute();
$result = $sql->get_result();
if ($result->num_rows > 0) {
    while($row = $result->fetch_assoc()) {
    $Resut[] = $row["name"];
    }
    echo json_encode($Result);
}
$conn->close();

?>

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.