【问题标题】:How to update parent table from partial view using Ajax如何使用 Ajax 从部分视图更新父表
【发布时间】:2016-02-28 14:26:28
【问题描述】:

我有一个表格,其中列出了系统中的课程,每个课程都有一个选择按钮(在一行中)。当我单击选择时,将显示该课程的注册用户。 Course 实体具有导航属性public List<CourseRegistration> CourseRegistrations { get; set; }

我有这个 ViewModel 用于此目的:

public class CourseIndexViewModel
{     
    public int SelectedCourseId { get; set; }

    public List<Course> Courses { get; set; }
}

就在注册列表(或注册)下方,我有一个文本框(用于关键字)和用于搜索用户注册的按钮。我使用 AJAX 执行控制器 (UserController) 的操作(我将关键字传递给该操作),该操作在数据库中搜索用户,并将结果集传递给局部视图,该视图返回一个用户表,每行都有 Enroll 按钮。

到目前为止一切正常。现在,我需要在 Partial View 中实现 Enroll 按钮。但是,我需要课程的 ID,它实际上在主视图中可用(即 SelectedCourseId)。有没有办法从局部视图访问该值?为此我必须(或应该)使用隐藏输入吗?

最大的挑战是在注册新用户后更新主视图中显示的注册列表。我想使用 Ajax 来防止页面刷新。

是否可行并建议使用 Ajax 从数据库中再次获取注册,并将主视图中现有的注册表替换为部分视图中生成的新表?

更新 这是主要视图:

@model EcholuMvc.Models.CourseIndexViewModel

<table class="table">
    <tr>
        <th></th>
        <th>
            CourseTitle
        </th>           
        <th></th>
    </tr>

    @foreach (var item in Model.Courses)
    {
        <tr @(Model.SelectedCourseId == item.CourseId ? "style=background-color:whitesmoke;" : "style=" )>
            <td>
                @Html.ActionLink("Select", "Index", new { courseId = item.CourseId })
            </td>
            <td>
                @Html.DisplayFor(modelItem => item.CourseTitle)
            </td>                
            <td>
                @Html.ActionLink("Edit", "Edit", new { id = item.CourseId }) |
                @Html.ActionLink("Delete", "Delete", new { id = item.CourseId })
            </td>
        </tr>
        if (Model.SelectedCourseId == item.CourseId)
        {
            <tr>
                <td>
                    <h4>Enrolled users:</h4>
                    <table class="table">
                        <tr>
                            <th>First name</th>
                            <th>Last name</th>                                
                            <th></th>
                        </tr>
                        @if (item.CourseRegistrations.Count > 0)
                        {
                            var registrations = item.CourseRegistrations;
                            foreach (var reg in registrations)
                            {
                                <tr>
                                    <td>
                                        @reg.Member.FirstName
                                    </td>
                                    <td>
                                        @reg.Member.LastName
                                    </td>                                        
                                    <td>
                                        @Html.ActionLink("Delete", "Delete", new { memberid = reg.MemberId, courseid = reg.CourseId })
                                    </td>
                                </tr>
                            }
                        }
                        else
                        {
                            <tr>
                                <td colspan="4">No enrollment!</td>
                            </tr>
                        }

                    </table>
                    <div class="container-fluid">
                        <div class="row">
                            <div class="col-sm-9">
                                <input id="txt_SearchUser" placeholder="Enter a name.." class="form-control " type="text" />
                            </div>
                            <input id="btn_SubmitUserSearch" class="btn btn-default btn-sm col-sm-3" type="button" value="Search" />
                        </div>
                        <div class="row">
                            <div id="div_UserSearchResults" class="col-sm-12">

                            </div>
                        </div>
                    </div>
                    <script>
                        $("#btn_SubmitUserSearch").click(function () {
                            $.ajax({
                                url: 'Account/SearchUsers',
                                contentType: 'application/html; charset=utf-8',
                                data: { keyword: $('#txt_SearchUser').val() },
                                type: 'GET',
                                dataType: 'html'
                            })
                            .success(function (result) {
                                $('#div_UserSearchResults').html(result);
                            })
                            .error(function (xhr, status) {
                                alert(status);
                            })
                        });
                    </script>
                </td>
            </tr>
        }
    }

</table>

还有,这里是部分视图:

@model IEnumerable<EcholuMvc.Models.ApplicationUser>

<table class="table-striped" >
@foreach (var item in Model) {
    <tr>
        <td>
            @Html.DisplayFor(modelItem => item.FirstName)
        </td>
        <td>
            @Html.DisplayFor(modelItem => item.LastName)
        </td>
        <td>
            <select id="drp_Role">
                <option value="Student" selected="selected">Student</option>
                <option value="Instructor">Instructor</option>
            </select>
        </td>
        <td>
            <input id="btn_Enroll" data-userid="@item.Id" type="button" />
        </td>
    </tr>
}

</table>

【问题讨论】:

  • 请向我们展示您视图中的相关 html 以及加载部分视图的 ajax 代码。
  • 是的,但不是再次构建主表您可以在同一个表中添加一个新条目,这样您根本不需要调用服务器来更新您的主表
  • @Shyju 我做到了!谢谢!
  • @Reddy 您的意思是使用 ajax 和 jquery 向表中添加新行?
  • 是的,使用 Jquery 只需在主表中添加一个新行。

标签: c# ajax asp.net-mvc partial-views


【解决方案1】:

如果您只是想在客户端选择 courseId(用于您的 ajax 提交新注册或任何其他事情),您可以在主视图中添加一个隐藏字段并在需要时从中读取。

@Html.HiddenFor(s=>s.SelectedCourseId)

现在,当您需要将它用于 ajax 帖子时,只需读取 this 的值并使用

var selectedCourseId=$("#s.SelectedCourseId").val();

但是,如果您出于某种原因想要在搜索功能中使用 courseId,您可以将选定的 courseId 作为参数传递给您的 ajax 调用。将课程 ID 作为 html 5 数据属性保存到您的搜索输入字段

<input id="txt_SearchUser" placeholder="Enter a name.."
               data-course="@item.CourseId" class="form-control " type="text" />

现在,当您进行 ajax 调用时,读取该值并发送它。

$("#btn_SubmitUserSearch").click(function () {
     $.ajax({
             url: 'Account/SearchUsers',
             data: { keyword: $('#txt_SearchUser').val(),
                     courseId:$('#txt_SearchUser').data("course") },
             type: 'GET',
             dataType: 'html'
            })
            .success(function (result) {
                $('#div_UserSearchResults').html(result);
            })
            .error(function (xhr, status) {
               alert(status);
           })
});

确保您的 SearchUsers 端点接受这个新参数并将其传递给它将呈现的结果局部视图。

public ActionResult SearchUsers(string keyword,int courseId)
{
  // to do : Do something with the passed values
  // to do : return something
}

我还假设,在您的 if 条件下,您只在页面中呈现一个搜索表单,因为您不能有重复的 id。还可以考虑使用 Url.Action 辅助方法生成正确的 url 到 action 方法,而不是像 this post 中解释的那样硬编码 url。

【讨论】:

  • 感谢@Shyju 的回答!在部分视图中注册新用户时,如何在父视图中更新课程注册列表?我应该只使用 ajax 和 jquery 插入新行吗?
  • 您正在进行 ajax 调用以添加新注册。因此,您在客户端拥有所有值。因此,要么为新行构建 html 标记并将其附加到表中(例如:$("#YourTableId").append("&lt;tr&gt;&lt;td&gt;Hi&lt;/td&gt;&lt;/tr&gt;"); 或当您进行 ajax 调用时,让服务器回复部分视图,这是新行的标记。
  • 我想如果我使用@item.CourseId 而不是$('#txt_SearchUser').data("course") } 进行ajax 调用应该没问题?谢谢!
  • @item.CourseId 是服务器代码并在服务器上执行。您无法从您的 js 代码再次执行该操作。这就是我们将它保存在输入字段的数据属性中的原因,剃须刀将正确呈现并且客户端脚本可以访问它。
  • 你推荐我使用Url.Action 方法。如果我要为按钮/链接进行 ajax 调用,我想知道是否可以不使用它。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多