【问题标题】:Is there a way to dynamically ajax add elements through jquery chosen plugin?有没有办法通过 jquery 选择的插件动态 ajax 添加元素?
【发布时间】:2012-03-29 19:10:08
【问题描述】:

我正在尝试通过 Harves (http://harvesthq.github.com/chosen/) 使用“Chosen”插件,它适用于我传递的静态选项集。但是,我想要的是,每当有人键入不在预填充选项中的内容时,它应该将其作为新选项发送到服务器并在成功响应时,我不仅想将其添加到有效列表中选项,但也让它选择它。

重新加载选项相当简单:

// In ajax response
var newOption = new Option("Text", __value__);
$("#tagSelection").append(newOption);
$("#tagSelection").trigger("liszt:updated");

但是,我不知道如何让“Chosen”插件选择这个作为值。我很想做类似的事情

$("#tagSelection").trigger("liszt:select:__value__"); 

或类似的东西。

有什么建议吗?

(ps:我正在尝试根据选择构建一个“标记”插件。因此,如果输入的标记不存在,它会将其添加到服务器然后立即选择它。)

【问题讨论】:

    标签: jquery jquery-plugins jquery-chosen


    【解决方案1】:

    我一直在这样做。我不喜欢 Shreeni 的设置选择线(无冒犯),所以我选择了

    $('#tagSelection').append(
        $('<option></option>')
            .val(data.Item.Id)
            .html(data.Item.Value)
            .attr("selected", "selected"));
    $("#tagSelection").trigger("liszt:updated");
    

    我个人认为它更干净(用多选框测试,效果很好)

    【讨论】:

    • 公平点,我将更改我的代码以反映这一点。此代码可能与新选项不起作用的 IE8 和更低版本兼容。
    【解决方案2】:

    这些是我为解决这个问题而对所选插件(jquery 版本)所做的全部更改

    Chosen.prototype.choice_build = function(item) {
      this.new_term_to_be_added = null; 
      // ....
    };
    
    Chosen.prototype.no_results = function(terms) {
      // ....
      no_results_html.find("span").first().html(terms);
      this.new_term_to_be_added = terms;
      return this.search_results.append(no_results_html);
    };
    
    
    Chosen.prototype.keydown_checker = function(evt) {
           // ...
            case 13:
              if(this.new_term_to_be_added != null &&  this.options.addNewElementCallback != null) {
                  var newElement = this.options.addNewElementCallback(this.new_term_to_be_added);
    
    
                  if(newElement!=null && newElement.length == 1) {
                      // KEY TO SOLVING THIS PROBLEM
                      this.result_highlight = newElement;
                      // This will automatically trigger the change/select events also. 
                      // Nothing more required.
                      this.result_select(evt);
                  }
                  this.new_term_to_be_added = null;
              }
              evt.preventDefault();
              break;
              // ...
    };
    

    this.new_term_to_be_added 维护当前键入的字符串,该字符串不在预定义选项中。

    options.addNewElementCallback 是调用函数的回调,以允许他们处理它(将其发送到服务器等),它必须是同步的。下面是骨架:

    var addTagCallback = function(tagText) {
        var newElement = null;
        $.ajax({url : that.actionUrl, 
            async : false, 
            dataType: "json",
            data : { // ....},
            success : function(response) {
            if(response) {
                                $('#tagSelection').append(
                                    $('<option></option>')
                                          .val(data.Item.Id)
                                          .html(data.Item.Value)
                                          .attr("selected", "selected"));
                $("#tagSelection").trigger("liszt:updated");
                // Get the element - will necessarily be the last element - so the following selector will work
                newElement = $("#tagSelection_chzn li#tagSelection_chzn_o_" + ($("#tagSelection option").length - 1));
            } else {
                // Handle Error
            }
        }});
        return newElement;
    };
    

    newElement 是一个 jquery 元素 - 选项列表中最新添加的 li 对象。

    通过这样做。result_highlight = newElement;和 this.result_select(evt);我告诉 Chosen 插件选择这个。无论是单选还是多选,这都有效。 Rifky 的解决方案仅适用于单选。

    【讨论】:

    • 为什么它“必须”同步?你可以很容易地异步编写。
    • 为什么不用这个扩展能力在 github 上 fork 主项目,或者你不向主存储库发送任何拉取请求?
    • 我不能让它工作,因为我不能应用这个:this.result_highlight = newElement; this.result_select(evt);从另一个函数,我需要通过覆盖选择来做到这一点吗?在这种情况下这是什么?我添加了我的元素,但我也添加了列表中的第一个元素。仅使用 $input.trigger("chosen:updated");
    • 看起来no_results 函数在 1.8.X 中已经发生了一些变化
    【解决方案3】:

    已创建包含您想要的功能的分支here。这种分叉被称为 koenpunt 分叉。

    您可以在 Harveshq github 网站上继续讨论此功能

    我对发生的事情的总结:

    1. 很多人都想要这个功能
    2. 一些人使用建议的解决方案创建了拉取请求
    3. 最好的解决方案是pull-request 166
    4. “选择”的作者决定不包含该功能
    5. koenpunt(pull-request 166 的作者)创建了一个 'chosen' 的分支
    6. 人们已经开始放弃'chosen'的收获版本,转而支持koenpunt fork

    【讨论】:

      【解决方案4】:

      自 1.0 版以来,上述一些建议不再适用。这就是所有需要的:

      --- /home/lauri/Downloads/chosen_v1.0.0 (original)/chosen.jquery.js
      +++ /home/lauri/Downloads/chosen_v1.0.0 (modified)/chosen.jquery.js
      @@ -408,8 +408,18 @@
                 break;
               case 13:
                 evt.preventDefault();
      -          if (this.results_showing) {
      +          if (this.results_showing && this.result_highlight) {
                   return this.result_select(evt);
      +          }
      +          var new_term_to_be_added = this.search_field.val();
      +          if(new_term_to_be_added && this.options.add_term_callback != null) {
      +              var newTermID = this.options.add_term_callback(new_term_to_be_added);
      +              if(newTermID) {
      +                this.form_field_jq.append(
      +                  $('<option></option>').val(newTermID).html(new_term_to_be_added).attr("selected", "selected")
      +                );
      +                this.form_field_jq.trigger("chosen:updated");
      +              }
                 }
                 break;
               case 27:
      

      选项如下:

      {add_term_callback: addTagCallback, no_results_text:'Press Enter to add:'}
      

      这意味着如果“Orange”不在水果列表中,它会简单地提示:

      按 Enter 键添加:“橙色”

      回调应通过任何必要的方式注册新术语,并返回新选项的 ID(或底层选择元素上下文中的值)。

      var addTagCallback = function(tagText) {
        // do some synchronous AJAX 
        return tagID;
      };
      

      【讨论】:

        【解决方案5】:

        我这样做很简单,效果很好:

        // this variable can be filled by an AJAX call or so
        var optionsArray = [ 
            {"id": 1, "name": "foo"}, 
            {"id": 2, "name": "bar"}
        ];
        
        var myOptions = "<option value></option>";
        for(var i=0; i<optionsArray.length; i++){
            myOptions +=  '<option value="'+optionsArray[i].id+'">'+optionsArray[i].name+'</option>';
        }
        
        // uses new "chosen" names instead of "liszt"
        $(".chosen-select").html(myOptions).chosen().trigger("chosen:updated");
        

        【讨论】:

          【解决方案6】:

          在您的 ajax 响应中,尝试

          var newOption = new Option("Text", __value__);  
          $("#tagSelection").append(newOption);  
          **/*  add this line */  
          $("#tagSelection").val(__value__);**  
          $("#tagSelection").trigger("liszt:updated");  
          

          【讨论】:

          • Rifky:快速说明:那行不通。我终于找到了一个解决方案,它需要对插件进行相当多的更改。一旦我得到一些喘息的空间,我会写一个详细的答案。 :)
          【解决方案7】:

          我认为这不是最佳做法,但此代码对我有用。数据返回有一个html标签&lt;option&gt;

          $.post("url.php",{data:data},function(data){
          $('.choosen').empty().append(data);
          $(".choosen").trigger("liszt:updated");
          });
          

          【讨论】:

            【解决方案8】:

            你不需要太大的压力,保持简单。您需要在选择框 html 中添加您的 ajax 响应,然后更新选择。

            这看起来像..

            代码:

            var baseURL='Your Url';
            
             $.ajax({
            
                       type: "POST",
            
                       url: baseURL+"Your function", //enter path for ajax
            
                       data: "id="+id,   //pass any details
            
                       success: function(response){   //get response in json_encode()formate
                              
                             var json_data = JSON.parse(response);
            
                              var i=0; var append='';
            
                              if((json_data['catss_data'].length > 0)){
            
                                  for(i=0;i < json_data['response_data'].length; i++){
            
                                      append+="<option value='"+json_data['response_data'][i].category_name+"'>"+json_data['response_data'][i].category_name+"</option>";
                                               // make response formate in option 
            
                                    }
            
                                $('#(selectbox-id)').html(append);   // enter select box id and append data in it
            
                                 }
            
                             }
            
                       $("#(selectbox-id)").trigger("chosen:updated");  // enter select box id and update chosen
            
               });   
            

            【讨论】:

              猜你喜欢
              • 2020-04-05
              • 1970-01-01
              • 1970-01-01
              • 2016-03-31
              • 1970-01-01
              • 2014-03-11
              • 2013-06-15
              • 1970-01-01
              • 1970-01-01
              相关资源
              最近更新 更多