【问题标题】:How to bind a list of lists in OnPost?如何在 OnPost 中绑定列表列表?
【发布时间】:2021-08-23 14:32:06
【问题描述】:

我正在使用 ASP.NET Core Razor Pages 并尝试绑定此属性,但是当我在 OnPost 函数处设置断点时,我得到一个空列表。

我正在使用 netcoreapp3.1

编辑.cshtml.cs
public class EditModel : PageModel
{
    [BindProperty]
    public List<List<Beam>> Beams { get; set; } 
    public void OnGet()
    {
    }
    public void OnPost()
    {
    }
}
编辑.cshtml
<form method="post" >

@for (int i = 0; i < 2; i++)
{
    @for (int j = 0; j < 2; j++)
    {
        <div class="form-group row">
            <label asp-for="Beams[i].ElementAt(j).BeamLayerName" class="col-md-3 col-form-label">Beam @(j+1) Layer Name</label>
            <div class="col-md-3">
                <input asp-for="Beams[i].ElementAt(j).BeamLayerName" class="form-control">
                <span asp-validation-for="Beams[i].ElementAt(j).BeamLayerName" class="alert-danger"></span>
            </div>
        </div>
        <div class="form-group row">
            <label asp-for="Beams[i].ElementAt(j).BeamDepth" class="col-md-3 col-form-label">Beam @(j+1) Depth </label>
            <div class="col-md-3">
                <input asp-for="Beams[i].ElementAt(j).BeamDepth" class="form-control">
                <span asp-validation-for="Beams[i].ElementAt(j).BeamDepth" class="alert-danger"></span>
            </div>
        </div>
        <div class="form-group row">
            <label asp-for="Beams[i].ElementAt(j).BeamWidth" class="col-md-3 col-form-label">Beam @(j+1) Width</label>
            <div class="col-md-3">
                <input asp-for="Beams[i].ElementAt(j).BeamWidth" class="form-control">
                <span asp-validation-for="Beams[i].ElementAt(j).BeamWidth" class="alert-danger"></span>
            </div>
        </div>
        <div class="form-group row">
            <label asp-for="Beams[i].ElementAt(j).BeamTopLevel" class="col-md-3 col-form-label">Beam @(j+1) Top Level </label>
            <div class="col-md-3">
                <input asp-for="Beams[i].ElementAt(j).BeamTopLevel" class="form-control">
                <span asp-validation-for="Beams[i].ElementAt(j).BeamTopLevel" class="alert-danger"></span>
            </div>
        </div>

    }
 }

<button type="submit" class="btn btn-info">Save changes</button>
光束类
public class Beam
{
    public int BeamId { get; set; }
    public string BeamLayerName { get; set; }
    public double BeamTopLevel { get; set; }
    public double BeamDepth { get; set; }
    public double BeamWidth { get; set; }
}

我做错了什么?

【问题讨论】:

    标签: c# asp.net .net-core razor-pages asp.net-core-3.1


    【解决方案1】:

    模型绑定器无法识别Beams[i].ElementAt(j) 语法。所以首先,尝试在任何地方将其更改为Beams[i][j]。由于它是列表列表,因此应该可以。

    如果这不可行或不起作用,请尝试使用编辑器模板。编辑器模板是更好的选择,也是推荐的方法,因为它非常适合此类场景。

    创建编辑器模板:

    1. 如果您的Pages 文件夹中不存在Shared 文件夹,请在其中创建它。
    2. 在此Shared 文件夹中,创建一个名为EditorTemplates 的文件夹。
    3. EditorTemplates 中,创建一个与模型同名的Razor 视图。这里是Beam,所以将文件命名为Beam.cshtml

    您的文件路径应如下所示:Pages/Shared/Beam.cshtml

    1. Beam.cshtml 文件中,将@model 指令添加为Beam,然后添加输入字段:
    @model Beam
    <input type="hidden" asp-for="BeamId">
    <div class="form-group row">
        <label asp-for="BeamLayerName" class="col-md-3 col-form-label">Beam Layer Name</label>
        <div class="col-md-3">
            <input asp-for="BeamLayerName" class="form-control">
            <span asp-validation-for="BeamLayerName" class="alert-danger"></span>
        </div>
    </div>
    <div class="form-group row">
        <label asp-for="BeamDepth" class="col-md-3 col-form-label">Beam Depth </label>
        <div class="col-md-3">
            <input asp-for="BeamDepth" class="form-control">
            <span asp-validation-for="BeamDepth" class="alert-danger"></span>
        </div>
    </div>
    <div class="form-group row">
        <label asp-for="BeamWidth" class="col-md-3 col-form-label">Beam Width</label>
        <div class="col-md-3">
            <input asp-for="BeamWidth" class="form-control">
            <span asp-validation-for="BeamWidth" class="alert-danger"></span>
        </div>
    </div>
    <div class="form-group row">
        <label asp-for="BeamTopLevel" class="col-md-3 col-form-label">Beam Top Level </label>
        <div class="col-md-3">
            <input asp-for="BeamTopLevel" class="form-control">
            <span asp-validation-for="BeamTopLevel" class="alert-danger"></span>
        </div>
    </div>
    
    

    这是单个梁的编辑器模板。现在要为列表中的每个项目重用此编辑器模板,您必须在 Edit.cshtml 中使用 Html.EditorFor() 方法:

    @for (int i = 0; i < 2; i++)
    {
        @Html.EditorFor(model => model.Beams[i])
    }
    

    这就是你所需要的。您可能已经注意到,您甚至不需要内部循环。 这里唯一的缺点是你不能使用像Beam @(j+1) 这样的索引。一种解决方案可能是创建一个 BeamViewModel 以包含索引,然后使用 List&lt;List&lt;BeamViewModel&gt;&gt;

    同样,有一些显示模板可以帮助重用模板来显示带有Html.DisplayFor() 的对象集合。更多关于这个here

    【讨论】:

      【解决方案2】:

      非常感谢您的帮助Amal K,我使用了这段代码,效果很好。

      <form method="post">
      
      @for (int i = 0; i < 2; i++)
      {
          @for (int j = 0; j < 2; j++)
          {
              <div class="form-group row">
                  <label asp-for="Beams[i][j].BeamLayerName" class="col-md-3 col-form-label">Beam @(j + 1) Layer Name</label>
                  <div class="col-md-3">
                      <input asp-for="Beams[i][j].BeamLayerName" class="form-control">
                      <span asp-validation-for="Beams[i][j].BeamLayerName" class="alert-danger"></span>
                  </div>
              </div>
              <div class="form-group row">
                  <label asp-for="Beams[i][j].BeamDepth" class="col-md-3 col-form-label">Beam @(j + 1) Depth </label>
                  <div class="col-md-3">
                      <input asp-for="Beams[i][j].BeamDepth" class="form-control">
                      <span asp-validation-for="Beams[i][j].BeamDepth" class="alert-danger"></span>
                  </div>
              </div>
              <div class="form-group row">
                  <label asp-for="Beams[i][j].BeamWidth" class="col-md-3 col-form-label">Beam @(j + 1) Width</label>
                  <div class="col-md-3">
                      <input asp-for="Beams[i][j].BeamWidth" class="form-control">
                      <span asp-validation-for="Beams[i][j].BeamWidth" class="alert-danger"></span>
                  </div>
              </div>
              <div class="form-group row">
                  <label asp-for="Beams[i][j].BeamTopLevel" class="col-md-3 col-form-label">Beam @(j + 1) Top Level </label>
                  <div class="col-md-3">
                      <input asp-for="Beams[i][j].BeamTopLevel" class="form-control">
                      <span asp-validation-for="Beams[i][j].BeamTopLevel" class="alert-danger"></span>
                  </div>
              </div>
      
          }
      }
      <button type="submit" class="btn btn-info">Save changes</button>
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2016-09-11
        • 2020-08-30
        • 2018-07-06
        • 2013-11-25
        • 1970-01-01
        • 1970-01-01
        • 2016-10-10
        • 2011-10-09
        相关资源
        最近更新 更多