如何通过 ajax post 多个附加输入字段值

How to post multiple appended input field values via ajax

所以,我一直在尝试在 html 页面中提供一个用户界面,用户可以在其中输入数字并点击应用 (使用 addRowsForm),查看各种输入字段的行被附加到另一个单独的表单 (名为 createRecordForm),然后通过 ajax.

我的问题是我无法找到对数据进行分组的方法 post 由于将添加的输入字段数量不可预测,具体取决于用户与页面的交互。非常感谢您的帮助。

这是我的代码:

addRowsForm

<form action="#" name="addRowsForm" id="addRowsForm" method="post">
   <div class="form-group">
      <input type="number" min="1" max="10" name="addRowCounter" id="addRowCounter">
   </div>
   <button type="submit" name="applyBtn" id="applyBtn">Apply</button>
</form>

createRecordForm

<table class="table table-bordered table-striped table-sm">
  <thead class="bg-brand-4th-color">
    <th>Link Type</th>
    <th>Link</th>
    <th>Recorded Time</th>
    <th>Video Visibility</th>
  </thead>
  <form action="" method="POST" name="createRecordForm" id="createRecordForm">
    <input type="hidden" name="ats_id" value="{{atsIdForFrag}}">
    <input type="hidden" name="tot_rows" value="">
    <tbody id="tBody">
    </tbody>
    <tfoot>
       {# submit btn #}
       <tr>
          <td colspan="4">
             <div class="form-group">
                <button class="btn btn-success" type="submit" name="create_recorded_session_btn" id="create_recorded_session_btn">Create</button>
              </div>
           </td>
        </tr>    
     </tfoot>
   </form>
</table>

Javascript 部分:

<script>
   $( document ).ready(
     function(){
          $("#addRowsForm").on("submit", function(e) {
          e.preventDefault();
          var rowCounter = $("input[name=addRowCounter]").val();
          $("input[name=tot_rows]").val(rowCounter);
          //reset any previous content
          $("#tBody").html('');
          for (var i = 1; i <= rowCounter; i++) 
          {
            var newRowContent = 
              "<tr><td><div class='form-group p-0 m-0'><select class='form-control' name='link_type_row_"+i+"' required><option value='google_drive' selected>Google Drive</option></select></div></td><td><div class='form-group p-0 m-0'><input class='form-control' type='text' name='link_row_"+i+"' value='' required></div></td><td><div class='form-group p-0 m-0'><input type='datetime-local' name='datetime_row_"+i+"' class='form-control' required/></div></td><td><div class='form-check'><input class='form-check-input' type='radio' name='visibilityRadio_row_"+i+"' id='showOption_row_"+i+"' value='show'><label class='form-check-label' for='showOption_row_"+i+"'>Show to student</label></div><div class='form-check'><input class='form-check-input' type='radio' name='visibilityRadio_row_"+i+"' id='dontShow_row_"+i+"' value='dont_show'><label class='form-check-label' for='dontShow_row_"+i+"'>Don\'t show to student</label></div></td></tr>";
              $("#tBody").append(newRowContent);
          }
    
          $("#createRecordForm").on("submit", function(e) {
            e.preventDefault();
    
            var ats_id = $("input[name=ats_id]").val();
            var tot_rows = $("input[name=tot_rows]").val();
      
            // here is my broblem, I need to change this hard-coded lines into dynamic data and process it in php
            var link_type_row_1 = $("select[name=link_type_row_1]").val();
            var link_row_1 = $("input[name=link_row_1]").val();
            var datetime_row_1 = $("input[name=datetime_row_1]").val();
            var visibilityRadio_row_1 = $("input[name=visibilityRadio_row_1]:checked").val();
            
            var link_type_row_2 = $("select[name=link_type_row_2]").val();
            var link_row_2 = $("input[name=link_row_2]").val();
            var datetime_row_2 = $("input[name=datetime_row_2]").val();
            var visibilityRadio_row_2 = $("input[name=visibilityRadio_row_2]:checked").val();
    
            var url = "{{ path('ao__frg_persist_st_rec_session')|escape('js') }}";
            var type = "POST";
    
            $.ajax({
              url : url,
              type: type,
              data : {
                'ats_id': ats_id,
                'tot_rows': tot_rows,
    
                'link_type_row_1': link_type_row_1,
                'link_row_1': link_row_1,
                'datetime_row_1': datetime_row_1,
                'visibilityRadio_row_1': visibilityRadio_row_1,
    
                'link_type_row_2': link_type_row_2,
                'link_row_2': link_row_2,
                'datetime_row_2': datetime_row_2,
                'visibilityRadio_row_2': visibilityRadio_row_2
              },
    
              success: function(returnedMsg) {
                // do something
              }
            });     
          });           
        });         
      });
    </script>

[更新:检查我在本段下方的回答] 如果我按照@Kinglish 的建议实施批处理方法,我最终将拥有一个大的单收音机,而每一行都应该有自己的收音机输入,与其他收音机分开。

[上述更新问题的解决方案] 所以我使用循环索引号来保留每行无线电输入的唯一名称和 ID。现在第 1 行的输入 name/id of visibilityRadio_row_1,第 2 行的 name/id 是 visibilityRadio_row_2.然后我使用 ^ 通配符选择器和 :checked 属性 来定位值每行中选中的无线电的数量独立于其他行。

let obj = [];
        $('.data-group').each(function() {
          obj.push({
            link_type: $(this).find('select[name="link_type_row"]').val(),
            link: $(this).find('input[name="link_row"]').val(),
            created_at: $(this).find('input[name="datetime_row"]').val(),
            is_active: $(this).find('input[name^="visibilityRadio_row"]:checked').val()
          })
        })

我会以不同的方式处理这个问题。考虑到您可以分批处理这些,而不是有限循环。在不重写脚本的情况下,看看这些是如何处理的。您最终会得到一组对象,这些对象按照它们在您的表单中的顺序出现。这消除了将数字附加到每个字段的混乱位。在接收这些的远程脚本中,您可以遍历它们,如果需要,在该点添加数字。

$(document).ready(function() {
  $('.submit').click(function() {
    let obj = [];
    $('.data-group').each(function() {
      obj.push({
        name: $(this).find('input[name="name"]').val(),
        gender: $(this).find('select[name="gender"]').val(),
        favorite_color: $(this).find('input[name="favorite_color"]').val()
      })
    })
    console.log('obj:', obj);
  })
})

// I accidentally did this in vanillaJS first, so for posterity, here is that version:
/*
window.addEventListener('DOMContentLoaded', () => {
  document.querySelector('.submit').addEventListener('click', () => {
    let obj = [];
    document.querySelectorAll('.data-group').forEach(e => {
      obj.push({
        name: e.querySelector('input[name="name"]').value,
        gender: e.querySelector('select[name="gender"]').value,
        favorite_color: e.querySelector('input[name="favorite_color"]').value
      })
    })
    console.log('obj:', obj);
  })
})
*/
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div class='data-group'>
  <input name='name' value='john' />
  <select name='gender'>
    <option selected value='this'>this</option>
    <option value='that'>that</option>
    <option value='other'>other</option>
  </select>
  <input name='favorite_color' value='blue' />
</div>


<div class='data-group'>
  <input name='name' value='mary' />
  <select name='gender'>
    <option value='this'>this</option>
    <option value='that' selected>that</option>
    <option value='other'>other</option>
  </select>
  <input name='favorite_color' value='green' />
</div>
<hr>
<button class='submit'>click</button>