在多个字段中进行Twitter Bootstrap的typead搜索

时间:2013-04-17 02:23:24

标签: javascript twitter-bootstrap bootstrap-typeahead typeahead.js

默认情况下,typeahead plugin使用单个数据源来获取结果。我想要的是它在多个领域内搜索,所以如果说,我有:

var items = [
    {'title': 'Acceptable', 'description': 'Good, but not great'}
]

它会搜索titledescription字段,最好是通过AJAX搜索。

这个插件可以实现吗?

2 个答案:

答案 0 :(得分:2)

Typeahead不支持在没有两次调整的情况下使用JSON对象。 Github中有很少的拉取请求,我有submitted one myself,但是,目前,您必须手动覆盖selectrender。此外,您还必须覆盖highlightermatchersorterupdater,但这些可以通过传递到预先输入的选项来完成。

var typeahead = control.typeahead({ /* ... */ }).data('typeahead');

// manually override select and render
//  (change attr('data-value' ...) to data('value' ...))
//  otherwise both functions are exact copies
typeahead.select = function() {
    var val = this.$menu.find('.active').data('value')
    this.$element.val(this.updater(val)).change()
    return this.hide()
};
typeahead.render = function(items) {
    var that = this

    items = $(items).map(function (i, item) {
        i = $(that.options.item).data('value', item)
        i.find('a').html(that.highlighter(item))
        return i[0]
    });

    items.first().addClass('active')
    this.$menu.html(items)
    return this
};

如果您需要其他人的帮助,请告诉我,但其要点是:

control.typehead({
    matcher: function (item) {
        var lcQuery = this.query.toLowerCase();
        return ~item.title.toLowerCase().indexOf(lcQuery)
            || ~item.description.toLowerCase().indexOf(lcQuery);
    }
};

我也有一个JFiddle example与我提出的拉取请求相关,但是2.3.1中没有排序功能,甚至没有接受拉取请求的3.x,所以你必须完全覆盖sorter以有效地重复我对上面的matcher所做的事情(在排序时检查两者)。

对于AJAX调用,您可以覆盖传入选项中的source方法以获取AJAX功能。如果不返回source调用,则会假定将使用结果调用第二个参数process,

control.typehead({
    minLength: 3,
    source: function(query, process) {
        $.ajax({
            url: url + encodeURIComponent(query),
            type: 'GET',
            success: process,
            error: function() { /* ... */ }
        });
    }
});

答案 1 :(得分:0)

Typeahead在v10.3中添加了对多字段搜索的支持 https://github.com/twitter/typeahead.js/pull/811

用法:
datumTokenizer: Bloodhound.tokenizers.obj.whitespace('title', 'description'),