以编程方式设置 Select2 ajax 的值

Posted

技术标签:

【中文标题】以编程方式设置 Select2 ajax 的值【英文标题】:Programmatically set the value of a Select2 ajax 【发布时间】:2014-10-13 06:18:06 【问题描述】:

我有一个 Select2 自动完成输入(通过 SonataAdmin 构建),但我终其一生都无法弄清楚如何以编程方式将其设置为已知的键/值对。

a JS Fiddle here 大致显示了我所拥有的。我想知道的是我可以将什么功能附加到按钮上,以便

Select2 字段向用户显示文本“NEW VALUE”,并且 当表单发送到服务器时,Select2 字段将提交值“1”

我已经尝试了 jQuery 和 Select2 dataval 方法的各种组合,针对页面上的各种输入调用,但似乎没有任何效果......肯定有什么方法可以做到这一点?

-- 编辑--

下面接受的答案非常有用,有助于阐明初始化选择的正确方法并解释 initSelection 的用途。

话虽如此,看来我最大的错误是我试图触发更改的方式。

我正在使用:

$(element).select2('data', newObject).trigger('change');

但这会导致 select2 的更改事件中出现一个空的 add 对象。

如果您改为使用:

$(element).select2('data', newObject, true);

然后代码可以正常工作,newObject 在 select2 的更改事件中可用,并且值设置正确。

我希望这些额外的信息对其他人有所帮助!

【问题讨论】:

【参考方案1】:

请注意,这是使用版本 4+ 测试的

找到这个讨论后我终于能够取得进展:https://groups.google.com/forum/#!topic/select2/TOh3T0yqYr4

最后一条评论指出了一种我能够成功使用的方法。

例子:

$("#selectelement").select2("trigger", "select", 
    data:  id: "5" 
);

这似乎是足够的信息来匹配 ajax 数据,并正确设置值。这对自定义数据适配器有很大帮助。

【讨论】:

作为注释,这将设置 适用于 v4。在谷歌搜索、搜索文档等 2 天后发现了这个。 谢谢!他们的文档说要使用 new Option 但这不适用于带有自定义模板的 AJAX 调用 它可以工作,但是当我尝试使用这种方法选择大约 30 个 select2 元素时,它需要 5 或 6 秒。我有一个表单,其中有一系列项目,因此在编辑该表单时使用此方法选择其他属性需要时间,所以对我不起作用。【参考方案2】:

注意:问题和本答案适用于 Select2 v3。 Select2 v4 的 API 与 v3 截然不同。

我认为问题出在initSelection 函数上。您是否使用该功能来设置初始值?我知道 Select2 文档听起来像是它的目的,但它也说“本质上这是一个 id-> 对象映射函数”,这不是您实现它的方式。

由于某种原因,对.trigger('change') 的调用会导致调用initSelection 函数,这会将所选值更改回“ENABLED_FROM_JS”。

尝试摆脱 initSelection 函数,而是使用以下方法设置初始值:

autocompleteInput.select2('data', id:103, label:'ENABLED_FROM_JS');

jsfiddle

注意:OP 提供了formatResultformatSelection 选项。如所提供的,这些回调函数期望项目具有“标签”属性,而不是“文本”属性。 对于大多数用户来说,应该是:

autocompleteInput.select2('data', id:103, text:'ENABLED_FROM_JS');

更多关于initSelection函数的信息:

如果您在Select2 documentation 中搜索“initSelection”,您会看到它在元素具有初始值以及调用元素的.val() 函数时使用。那是因为这些值只包含一个 id 而 Select2 需要整个数据对象(部分是为了显示正确的标签)。

如果 Select2 控件显示静态列表,initSelection 函数将很容易编写(看起来 Select2 可以为您提供它)。在这种情况下,initSelection 函数只需在数据列表中查找id 并返回相应的数据对象。 (我在这里说“返回”,但它并没有真正返回数据对象;它会将它传递给回调函数。)

在您的情况下,您可能不需要提供 initSelection 函数,因为您的元素没有初始值(在 html 中)并且您不会调用它的 .val() 方法。只需继续使用.select2('data', ...) 方法以编程方式设置值即可。

如果您要为自动完成(使用 ajax)提供 initSelection 函数,它可能需要进行 ajax 调用来构建数据对象。

【讨论】:

顺便说一句,是否有任何文档说明“本质上这是一个 id-> 对象映射函数”的含义(以及如何在该上下文中将其用于自动完成字段)?跨度> initSelection 在 Select2 4.0 中已弃用。这已被 数据适配器 上的 current 方法取代,并且仅在完整版本中可用 请更新小提琴 - 资源加载失败并显示 404 @Zanshin13 - 我更新了 jsfiddle 中外部资源的 URL,但我认为它实际上没有起作用,因为 ajax 调用无效。【参考方案3】:

要设置初始值,您需要使用 jQuery 将必要的选项标签添加到 select 元素,然后使用 select2 的 val 方法将这些选项定义为选中,最后触发 select2 的 'change' 事件。

1.-$('#selectElement').append('<option value=someID>optionText</option>');
2.-$('#selectElement').select2('val', someID, true);

第三个布尔参数告诉 select2 触发更改事件。

欲了解更多信息,请参阅https://github.com/select2/select2/issues/3057

【讨论】:

您不能将选择元素用于远程数据 (ajax)。【参考方案4】:

小心,“已验证”的评论有误。

autocompleteInput.select2('data', id:103, label:'ENABLED_FROM_JS');

正确的做法是

autocompleteInput.select2('data', id:103, text:'ENABLED_FROM_JS');

使用 text 代替 label

【讨论】:

对我来说是名称而不是文本/标签 :) 如果您查看 OP 的 jsfiddle,您会看到 OP 提供了 formatResultformatSelection 选项。这些函数的编写方式,他们希望项目具有“标签”属性,而不是“文本”属性。我已经添加到我的答案中,以向其他人说明这一点。【参考方案5】:

使用 Select2 版本 4+,实际上您不需要做任何特别的事情。最后带有“更改”事件触发器的标准 jQuery 将起作用。

var $select = $("#field");
var items = id: 1, text: "Name"; // From AJAX etc
var data = $select.val() || [];    // If you want to merge with existing

$(items).each(function () 
  if(!$select.find("option[value='" + this.id + "']").length) 
    $select.append(new Option(this.text, this.id, true, true));
  
  data.push(this.id);
);

$select.val(data).trigger('change'); // Standard event notifies select2

Select2 文档中有一个基本示例: https://select2.org/programmatic-control/add-select-clear-items

【讨论】:

【参考方案6】:

从他们的例子 https://select2.github.io/examples.html

程序化访问:

var $example = $(".js-example-programmatic").select2();
var $exampleMulti = $(".js-example-programmatic-multi").select2();
$(".js-programmatic-set-val").on("click", function ()  $example.val("CA").trigger("change"); );
$(".js-programmatic-open").on("click", function ()  $example.select2("open"); );
$(".js-programmatic-close").on("click", function ()  $example.select2("close"); );
$(".js-programmatic-init").on("click", function ()  $example.select2(); );
$(".js-programmatic-destroy").on("click", function ()  $example.select2("destroy"); );
$(".js-programmatic-multi-set-val").on("click", function ()  $exampleMulti.val(["CA", "AL"]).trigger("change"); );
$(".js-programmatic-multi-clear").on("click", function ()  $exampleMulti.val(null).trigger("change"); );

【讨论】:

【参考方案7】:

您所要做的就是设置值然后执行:$ ('#myselect').select2 ();$ ('select').select2 ();。 而且一切都更新得很好。

【讨论】:

【参考方案8】:

如果您从小提琴中删除.trigger('change'),它会记录Object id: 1, label: "NEW VALUE"(需要单击两次,因为记录是在值更改之前)。这就是你要找的吗?

【讨论】:

是的,我也删除了 .trigger('change');,它对我有用 (Chrome) 不幸的是,我需要触发更改,而 JohnS 的答案触及问题的根源,因此我接受了该答案。【参考方案9】:

当使用带有多个选项的 select2 时,请使用以下构造:

$(element).select2("data", $(element).select2("data").concat(newObject), true);

jqueryselect2multiplesetconcatenation

【讨论】:

【参考方案10】:

就是这样:

$("#tag").select2('data',  id:8, title: "Hello!");

【讨论】:

【参考方案11】:

适用于 3.5.3 版

    $(".select2").select2('data',id:taskid,text:taskname).trigger('change');

基于John S' answer 。只有在初始化 select2 时 initSelection 选项未初始化时,上述方法才有效。

$(".select2").select2(
      //some setup
)

【讨论】:

【参考方案12】:

对于仍在使用 3.5 或更高版本的用户。请确定您如何将 select2.js 引用到您的页面。如果您使用异步或延迟加载。此插件的行为可能有所不同。

想提一下。

【讨论】:

【参考方案13】:

在我的情况下,我能够使用 php 将预选选项呈现到 HTML 服务器端。

在我的页面加载过程中,我已经知道了option的值,所以我的&lt;select name="team_search"&gt;&lt;/select&gt;变成了下面这样;

        <select name="team_search">
            <?php echo !empty($preselected_team) 
                    ? '<option selected="selected" value="'. $preselected_team->ID .'">' . $preselected_team->team_name . '</option>' 
                    : null ?>
        </select>';

如您所见,当我有可用的$preselected_team 时,我会在带有selected 属性、value 和标签集的选项中呈现。而且,如果我没有值,则不会呈现选项。

这种方法可能并不总是可行(并且在 OP 的情况下没有提到),但它确实带来了额外的好处,即在 javascript 执行之前准备好页面加载。

【讨论】:

【参考方案14】:

添加一个带有 id 和文本的新选项

let $newOption = $("<option selected='selected'></option>").val(1).text('New Text goes here');
$("#selector").append($newOption).trigger('change');

【讨论】:

以上是关于以编程方式设置 Select2 ajax 的值的主要内容,如果未能解决你的问题,请参考以下文章

如何以编程方式将搜索查询注入 Select2 v4?

不使用jQuery以编程方式控制Select2

如何在 select2 类型提前搜索中设置选项值以及如何从 ajax 数据添加选项组

如何以编程方式更改 select2 值

jquery Select2 Ajax - 如何设置值(initSelection)

select2 和表单更改事件