流程上的Bootstrap Multiselect更新选项列表

时间:2013-12-05 13:48:27

标签: javascript jquery ajax twitter-bootstrap

我使用bootstrap multi-select,我想用ajax

更新flow上的选项

要在init上填充我的多选我

<select name="model" class="multiselect" multiple="multiple">
                <? foreach ($sel_models as $mod) { ?>
                    <option value="<?= $mod ?>" <?= ($mod == $params['model']) ? 'selected' : '' ?>><?= $mod ?></option>
                <? } ?>    
</select>  

然后在事件中我想用以下ajax更新我的选项列表

我试图使用重建方法但不会在创建后触发下拉列表

 $.ajax({
        type: 'post',
        url: "helper/ajax_search.php",
        data: {models: decodeURIComponent(brands)},
        dataType: 'json',
        success: function(data) {
            $('select.multiselect').empty();
            $('select.multiselect').append(
                    $('<option></option>')
                    .text('alle')
                    .val('alle')
                    );

            $.each(data, function(index, html) {
                $('select.multiselect').append(
                        $('<option></option>')
                        .text(html.name)
                        .val(html.name)
                        );
            });

            $('.multiselect').multiselect('rebuild')
        },
        error: function(error) {
            console.log("Error:");
            console.log(error);
        }
    });

使用firebug,我可以看到列表已生成,但在select时将不会显示

4 个答案:

答案 0 :(得分:21)

在我可以阅读的文档中:

.multiselect('setOptions',options) 用于在初始化多选后更改配置。这可能与.multiselect('rebuild')结合使用。

也许您无法通过初始方式更改窗口小部件数据。以正确的方式使用setOptions方法。

其他:按照自己的方式,也许你应该考虑销毁你的小部件.multiselect('destroy')并在之后重新创建它。

评论后更新:

在doc :(你已经链接)

  

以下列方式提供用于构建选择选项的数据:

var data = [
    {label: "ACNP", value: "ACNP"},
    {label: "test", value: "test"}
];
$("#multiselect").multiselect('dataprovider', data);

所以: 当你从ajax调用中获取数据时,你必须创建一个对象数组(它是你想要的选项中的选项),格式为

var data = 
[
    {label: 'option1Label', value: 'option1Value'},
    {label: 'option2Label', value: 'option2Value'},
    ...
]

创建对象数组后,只需调用方法

即可
$("#multiselect").multiselect('dataprovider', data);

数据是您的对象数组。

我希望我很清楚:/

答案 1 :(得分:9)

作为multiselect('dataprovider',data)的替代方法,您可以使用jquery构建列表,与您在问题中的方式完全相同。您需要做的唯一更改是延迟重建,直到ajax请求完成为止。

var buildDrivers = $.getJSON('resources/orders/drivers.json', function(data) { 
   $.each(data, function(i, driver) {
      $('#toolbar select[name="drivers"]').append('<option>'+driver+'</option>');
   });
});
buildDrivers.complete(function() {
    $('.multiselect').multiselect('rebuild');
});

请参阅http://api.jquery.com/jquery.getjson/了解文档

答案 2 :(得分:0)

我已经过滤并从服务器端获取选项后添加了更新选项的功能。该解决方案继承了注入新选项的概念,破坏了选择并再次初始化它。

我考虑到了:

  1. 考虑现有的选定选项,必须保留。
  2. 删除重复选项(可能是已经选择的冲突和来自服务器的新冲突)。
  3. 更新后保持选项托盘打开。
  4. 重新分配搜索文本框中的上一个文字&amp;专注于它。
  5. 只需添加&#39; updateOptions&#39;作为“刷新”之后的功能函数以及两个辅助函数如下:

    updateOptions: function (options) {
            var select = this.$select;
            options += this.getSelectedOptionsString();
            var selectedIds = select.val(),
                btnGroup = select.next('.btn-group'),
                searchInput = btnGroup.find('.multiselect-search'),
                inputVal = searchInput.val();
    
            options = this.removeOptionsDuplications(options);
            if (!options) {
                options = '<option disabled></option>';
            }
    
            // 1) Replacing the options with new & already selected options
            select.html(options);
    
            // 2) Destroyng the select
            select.multiselect('destroy');
    
            // 3) Reselecting the previously selected values
            if (selectedIds) {
                select.val(selectedIds);
            }
    
            // 4) Initialize the select again after destroying it
            select.multiselect(this.options);
    
            btnGroup = select.next('.btn-group');
            searchInput = btnGroup.find('.multiselect-search');
    
            // 5) Keep the tray options open
            btnGroup.addClass('open');
    
            // 6) Setting the search input again & focusing it
            searchInput.val(inputVal);
            searchInput.focus();
        },
        getSelectedOptionsString: function () { // Helper
            var result = '',
                select = this.$select,
                options = select.find('option:selected');
    
            if (options && options.length) {
                $.each(options, function (index, value) {
                    if (value) {
                        result += value.outerHTML;
                    }
                });
            }
    
            return result;
        },
        removeOptionsDuplications: function (options) { // Helper
            var result = '',
                ids = new Object();
    
            if (options && options.length) {
                options = $(options);
                $.each(options, function (index, value) {
                    var option = $(value),
                        optionId = option.attr('value');
    
                    if (optionId) {
                        if (!ids[optionId]) {
                            result += option[0].outerHTML;
                            ids[optionId] = true;
                        }
                    }
                });
            }
            return result;
        },
    

    <强>演示:

    州:

    &#34;选项1&#34;

    $('#select').multiselect('updateOptions', '<option value="2">Option 2</option>');
    

    州:

    &#34;选项2&#34;

    &#34;选项1&#34;

答案 3 :(得分:0)

我认为这是在运行中(使用ajax或任何其他侦听器)向现有Bootstrap MultiSelect添加选项的简便方法。

以下是添加选项的简化示例:

function addOptionToMultiSelect(multiselectSelector, value, selected) {
    var data = [];
    $(multiselectSelector + ' option').each(function(){
        var value = $(this)[0].value;
        var selected = $(this)[0].selected;
        data.push({label: value, value: value, selected: selected});
    });

    // Add the new item
    data.push({label: value, value: value, selected: selected});

    $(multiselectSelector).multiselect('dataprovider', data);
}

为简单起见,我假设选项中的标签和值都相同。请注意,已选择的选项是通过从现有选项中读取所选属性来处理的。您可以通过跟踪禁用属性和其他属性来使其更复杂。

示例:

addOptionToMultiSelect('#multiselect-example', 'new-option', true);