如何在 ajax 调用中传递具有列表类型 属性 的对象

How to pass an object having a list type property in a ajax call

我知道 This type of question 之前有人问过,但我不明白如何用已经提供的答案解决问题。甚至不知道在哪里编写那些 ModelBinder 代码。所以我只会描述我的问题。 我有一个视图,它被强类型化为具有列表 属性(关联关系)的模型。

public class Sales
{
    public int SalesSl { get; set; }
    public double TotSalAmt { get; set; }
    public double TotCashRec { get; set; }
    public double TotVat { get; set; }
    public double TotDiscnt { get; set; }
    public int CustomerSupplyId { get; set; }
    public int ProductId { get; set; }
    public double SalesRt { get; set; }
    public double SalesQty { get; set; }
    public double PurchaseRt { get; set; }
    public double ProductDisAmt { get; set; }
    public double ProductVat { get; set; }
    public double LaborCost { get; set; }
    public string SalesNote { get; set; }
    public int SalesIndex { get; set; }
    public List<AddedProductView> AddedProductViews { get; set; }

    public Sales()
    {
        AddedProductViews = new List<AddedProductView>();
    }
}
  [Serializable]
public class AddedProductView
{       
    public int ProductId { get; set; }
    public string ProductName { get; set; }
    public double Quantity { get; set; }
    public double Unit { get; set; }
    public string UnitDescription { get; set; }
    public double Rate { get; set; }
    public double Vat { get; set; }
    public double Discount { get; set; }
    public double NetAmount { get; set; }
    public double Total { get; set; }
    public int SalesIndex { get; set; }
}

现在,当我将销售模型传递给视图时没有问题。它显示了已包含在 AddedProductViews 中的所有产品。 观点:

<form id="SalesModForm">
    <div>
        <div class="col-md-9 col-md-offset-0 panel panel-success">
            <div class="panel-heading">
                Purchase Product
            </div>
            <div class="panel panel-success">
                @Html.HiddenFor(model => model.IndexSl)
            <table>
                <tr>
                    <td>
                        @Html.TextBoxFor(model => model.SalesSl, null, new { style = "width:120px" })
                    </td>
                    <td>
                </tr>
                <tr>
                    <td>
                        @Html.LabelFor(model => model.CustSupplyId)
                    </td>
                    <td>
                        @Html.TextBoxFor(model => model.CustSupplyId, null, new { style = "width:120px" })
                    </td>
                </tr>
                <tr>
                    <td>
                        @Html.LabelFor(model => model.ProductId) <p class="indent"></p>
                    </td>
                    <td>
                        @Html.TextBoxFor(model => model.ProductId, null, new { style = "width:120px" })
                    </td>
                    <td>
                        @Html.Label("Qty")
                        @Html.TextBoxFor(model => model.SalesQty, null, new { style = "width:60px" })
                    </td>
                    <td>
                        @Html.Label("Rate")
                        @Html.TextBoxFor(model => model.SalesRt, null, new { style = "width:60px" })
                    </td>
                    <td>
                        <input type="button" value="Add" id="btnAddToCartMod" style="width:100px" />
                    </td>
                </tr>
            </table>
            <hr />
            <table border="1">
                <thead>
                    <tr>
                        <th>Product Name</th>
                        <th>Quantity</th>
                        <th>Unit</th>
                        <th>Rate</th>
                        <th>Total</th>
                        <th>Vat</th>
                        <th>Discount</th>
                        <th>Net Amount</th>
                        <th>Action</th>
                    </tr>
                </thead>
                <tbody>
                    @foreach (AddedProductView sIAM in Model.AddedProductViews)
                    {
                        <tr>
                            <td>
                                @sIAM.ProductName
                            </td>
                            <td>
                                @sIAM.Quantity
                            </td>
                            <td>
                                @sIAM.Unit
                            </td>
                            <td>
                                @sIAM.Rate
                            </td>
                            <td>
                                @sIAM.Total
                            </td>
                            <td>
                                @sIAM.Vat
                            </td>
                            <td>
                                @sIAM.Discount
                            </td>
                            <td>
                                @sIAM.NetAmount
                            </td>
                            <td>
                                @Html.ActionLink("Remove", "UpdateProductInfo", new { salesSl = @Model.SalesSl, productId = @sIAM.ProductId, salesDt = @Model.SalesDt })
                            </td>
                        </tr>
                    }
                </tbody>
            </table>
        </div>           

<div>
  <input type="submit" value="Sale" class="btn btn-success" id="btnSalesMod" />
</div>

当我点击 删除 AcionLink 时,模型数据 (sales.AddedProductViews) 被更改。现在,当我单击 btnSalesMod 时,我希望修改后的销售数据将在以下脚本的帮助下保存。

 <script>
    $(document).ready(function () {
        $('#btnAddToCartMod').click(function () {
            var data = $('#SalesModForm').serialize();
            $.ajax({
                type: 'Post',
                url: '/Sales/Index',
                data: data,
                success: function () {
                    window.location = '/Sales/Index';
                }
            });
        });
    });
</script>

但是当我调试时,控制器的 ActionResult 参数接收到所有销售数据,除了 sales.AddedProductViews 计数为 0,这意味着参数未接收AddedProductViews 属性 的任意值。 在控制器中:

[HttpPost]
    public ActionResult Index(Sales sales)
    {
        //no data in sales.AddedProductViews
        //sales.AddedProductViews count = 0;
        return View();
    }

所以,现在我的问题是如何获取视图中 AddedProductViews 中的数据。

或者有没有其他方法可以将 AddedProductViews 数据传递给控制器​​?? 感谢任何帮助。

您需要了解模型绑定在 MVC 中的工作原理。当您使用任何 HTML Helper 时,该控件的名称将设置为使用的模型 属性。例如

@Html.TextBoxFor(model => model.SalesSl, null, new { style = "width:120px" })

将呈现带有 type="text"name="SalesSl" 的输入元素,当您将 post 表单返回服务器时,带有 name="SalesSl" 的控件的值将得到绑定到名为 SalesSl.

的模型 属性

但是当你使用类似下面的东西时:

<td>@sIAM.ProductName</td>

没有创建名称设置为模型 属性 名称的控件。

您需要使用 for 循环而不是 foreach 循环,并且在循环中您需要为每个要提交回服务器的 AddedProductView 属性执行类似的操作:

<td>
    @Html.Hidden("AddedProductViews[@index].ProductName", @Model.AddedProductViews[index].ProductName);
    @Model.AddedProductViews[index].ProductName
</td>

这些链接应该会有帮助:

  • Manually binding complex model array to controller action
  • Model Binding To A List
  • MVC .NET Model Binding to Array on the fly