【问题标题】:JqGrid searchoptions with select2 existing value具有 select2 现有值的 JqGrid 搜索选项
【发布时间】:2018-08-23 07:04:16
【问题描述】:

我正在尝试为 JqGrid 过滤器表单集成 select2。我正在使用 JqGrid min 4.6 & Select2 min 4.0.1。过滤器工作正常,但是一旦关闭并重新打开过滤器表单,我就无法检索通过 select2 设置的值。即 dataInit e1 不返回选择输入的现有值。我一定是做错了什么?

JqGrid 列模型:

        {
            name: 'CurrencyID', hidden: true, search: true, stype: 'select', searchtype: 'number', searchoptions: {
                searchhidden: true,
                sopt: ['eq', 'ne'],
                dataInit: function (el) {
                    intiGridFilterSelecr2Field(el, paramFromView.CurrencyOptions);
                }
            },
            searchrules: { required: true }
        },

参数:

@section scripts{
<script>
   var paramFromView = {
        CurrencyOptions: {
            searchURL: '@Url.Action("GetCurrency", "Controller")',
            detailURL: '@Url.Action("CurrencyDetailsJson", "Controller")',
            idField: 'CurrencyID',
            txtField: 'Description'
        }
   };
</script>
}

Select2 助手:

function intiGridFilterSelecr2Field(element, options) {
var comboPageSize = 15;
var quietMillis = 200;
var placeHolderText = 'Choose...'

var defaults = {
    searchURL: '',
    detailURL: '',
    idField: '',
    txtField: ''
};
var options = $.extend({}, defaults, options);
var select2Element = $(element);

select2Element.select2({
    width: 'element',
    minimumInputLength: 1,
    placeholder: placeHolderText,
    ajax: {
        url: options.searchURL,
        dataType: 'json',
        quietMillis: quietMillis,
        cache: false,
        data: function (params) {
            return {
                name: params.term,
                page: params.page,
                pageSize: comboPageSize
            };
        },
        processResults: function (data) {
            var more = (data.page * comboPageSize) < data.total;

            var resultsArr = [];
            for (var i = 0; i < data.result.length; i++) {
                resultsArr.push({ id: data.result[i][options.idField], text: data.result[i][options.txtField] });
            }
            return { results: resultsArr, more: more };
        }
    },
}).each(function (index, element) {
    var idCombo = $(this);
     // The problem is that idCombo.val() is always empty.
     // element:select2-hidden-accessible
    if (idCombo.val() != null && idCombo.val().length > 0) {
        $.ajax(options.detailURL, {
            data: {
                id: idCombo.val()
            },
            dataType: 'json',
            cache: false
        }).done(function (data) {
            var optselected = select2Element.find('option').filter(function () { return this.value == data[idField] && this.text == data[txtField] && this.selected })
            if (optselected == undefined || optselected.length == 0) {
                var $optionContact = $("<option selected></option>").val(data[idField].toString()).text(data[txtField]);
                var toBeRemoved = select2Element.find('option').filter(function () { return this.value == data[idField] });
                if (toBeRemoved != undefined) {
                    toBeRemoved.remove();
                }
                select2Element.append($optionContact).trigger('change.select2');
            }
        });
    }

  });
}

设置过滤器时...

加载现有过滤器时。如何将此 CurrencyID = 1 传递给 select2 助手?

更新:

根据 Oleg 的回答,我将代码更新如下。

            {
            name: 'CurrencyID', hidden: true, searchtype: 'number', search: true,
            stype: "select", searchoptions: {
                searchhidden: true,
                sopt: ["eq", "ne"],
                dataUrl: paramFromView.CurrencyOptions.searchURL,
                buildSelect: function (data) {
                    var obj = jQuery.parseJSON(data);
                    var i, options = [];
                    for (i = 0; i < obj.result.length; i++) {
                        options.push("<option value='" + obj.result[i][paramFromView.CurrencyOptions.idField] + "'>" +
                            obj.result[i][paramFromView.CurrencyOptions.txtField] + "</option>");
                    }
                    return "<select>" + options.join("") + "</select>";
                },
                noFilterText: "Any",
                selectFilled: function (options) {
                    setTimeout(function () {
                        $(options.elem).select2({
                            width: 'element',
                        });
                    }, 0);
                }
            },
            searchrules: { required: true }
        },

我几乎完成了我想要实现的目标。但是,我仍然面临一些困难。

  1. 最初加载过滤器时,在下拉列表中选择了值,但查询值为空。即如果用户在过滤器表单加载后不久点击查找按钮,则不会设置过滤器。

  2. 我仍然无法让 select2 样式正常工作。

【问题讨论】:

    标签: asp.net-mvc jqgrid jquery-select2-4


    【解决方案1】:

    我可以演示如何将 select2 与我开发的 jqGrid 的 free jqGrid fork 一起使用。我从老版本4.14.1(当前发布版本是4.15.3)的README拿到demo,修改了一下,演示了select2的用法。

    代码的主要部分可以是

    stype: "select",
    searchoptions: {
        sopt: ["eq", "ne"],
        ...
        selectFilled: function (options) {
            setTimeout(function () {
                $(options.elem).select2({
                    width: "100%"
                });
            }, 0);
        }
    }
    

    https://jsfiddle.net/Lae6kee7/2/。您可以尝试在“发货方式”列的过滤器工具栏中选择一个选项,然后打开搜索对话框。您将看到 select2 将选择相同的选项。

    如果您要通过 select2 发布的 Ajax 请求加载数据,那么您的代码将会复杂得多。重要的是要了解这种方式实际上只需要非常大的可能值集。例如,我的意思是大于 100000 个项目的项目数。另一方面,大多数用例所需的选项少于 1000 个。在这种情况下,将所有数据加载为 select 的选项,然后将 select 转换为 select2 会更有效。从用户的角度来看,使用本地选择的 select2 工作得更快。

    在我看来,如果您使用dataUrl 而不是select2ajax 选项,代码会更容易。您可以使用dataUrl 从服务器返回所有不同的值,这些值可以在select2 中使用,并使用buildSelect 从服务器返回的JSON 数据构建&lt;select&gt;。演示 https://jsfiddle.net/Lae6kee7/23/ 演示了这一点。我为 JSFiddle 做了演示,它支持 Echo 服务(参见here),它允许模拟服务器响应。您的真实代码应该主要只包含dataUrlbuildSelectselectFilled 的代码,我在上面包含了这些代码。

    此外,我建议您考虑使用&lt;datalist&gt;(例如,参见here),这可能是select2 的一个很好的替代方案。所有现代网络浏览器都包含对&lt;datalist&gt;native 支持,因此&lt;datalist&gt; 的工作速度非常快。尝试在我的演示的第一个 Client 列中搜索。您将看到与 select2 非常接近的控件。 &lt;datalist&gt; 的另一个优点:不能只搜索精确的预定义值,例如 test10test11test12,而是搜索子字符串,例如 1。比较

    【讨论】:

    • 您好,Oleg,感谢您为 JqGrid 所做的所有工作。我想你的答案我差不多了。两个问题。 Q1:我只能让 select2 样式与 dataInit 一起使用,但不能与 selectFilled 一起使用。 Q2:最初加载过滤器时,即使在下拉列表中设置了值,查询也是空的。有什么想法吗?
    • 请注意我指的是这个:jsfiddle.net/Lae6kee7/23 选项。
    • @ecasper:不客气!对不起,但我不明白你目前的问题。您在测试中使用了哪个版本的 jqGrid?演示jsfiddle.net/Lae6kee7/23中究竟存在什么问题?应该执行哪些步骤来重现问题?我所做的是 1)在过滤器工具栏中设置一些过滤器(例如,客户端包含“测试”,关闭为假,通过“TNT”运送)2)打开搜索对话框。我看到过滤器和 select2 包含选择的 TNT。可以直接在加载时执行相同操作。见jsfiddle.net/Lae6kee7/29。只需在演示中打开搜索对话框
    • 我正在使用 select2 4.0.3 和 JQgrid 4.6。请查看我更新的代码。第一个问题可以在演示 jsfiddle.net/Lae6kee7/23 中模拟。但我不确定为什么 select2 样式不适用。
    • @ecasper:抱歉,我开始回答了,我使用的是我开发的 free jqGrid fork 的当前版本 4.15.3。您在关于 min 4.6 和 Select2 min 4.0.1 的问题中写道。 jqGrid 4.6 已经死了,它已经 4 岁多了。免费的jjqGrid是兼容jqGrid 4.6的,但是我重写了很多源代码端口,对jqGrid CSS做了很多改动。
    猜你喜欢
    • 2016-12-01
    • 2020-12-17
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-10-22
    • 2014-12-22
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多