В основном мой вопрос касается того, как обрабатывать результаты PartialView. Моя текущая (фиктивная) страница составлена следующим образом:
Индекс.cshtml
@model SomeModel
@ {
ViewBag.Title = "";
Layout = "~/Views/Shared/_Layout.cshtml";
}
...(Shortened code)
@using (Html.BeginForm ()) {
@Html.EditorFor (model => model.Id, new { htmlAttributes = new { @class = "form-control", @id = "Id", @type = "text" } })
@Html.EditorFor (model => model.Name, new { htmlAttributes = new { @class = "form-control", @id = "Name", @type = "text" } }) <
<input type = "submit" value = "Search" / >
}
//The area where I want to place the PartialView result
<div class = "row">
@{Html.RenderAction("List", "Controller");}
</div>
И, наконец, мой List.cshtml
@model SomeViewModel
<table class = "table-bordered table table-hover m-2" id = "table">
<thead class = "thead-light">
<tr>
<th scope = "col" class = "align-middle">#</th>
<th scope = "col" class = "align-middle">Field </th>
<th scope = "col" class = "align-middle">Field </th>
<th scope = "col" class = "align-middle">Field </th>
<th scope = "col" class = "align-middle">Field </th>
<th scope = "col" class = "align-middle">Field </th>
<th scope = "col" class = "align-middle">Field </th>
<th scope = "col" class = "align-middle">Field </th>
<th scope = "col" class = "align-middle">Field </th>
</tr>
</thead>
<tbody>
//A @foreach for each item in the model, with <td> tags
</tbody>
</table>
Что я хочу, так это то, что когда я нажимаю кнопку «Поиск» на странице Index.cshtml, она должна получить 2 поля, используемые для поиска (идентификатор и имя), и перечислить результат на той же странице в результате контроллера списка.
Но в настоящее время он делает следующее: когда я нажимаю кнопку, он перенаправляет меня на /my/site/list, который буквально является результатом List.cshtml, что приводит к неформатированной странице только с таблицей.
Я уже пробовал следующий код в index.cshtml
<script>
var url = '@Url.Action("List", "Controller")';
$('form').submit(function() {
if (!$(this).valid()) {
return false;
}
var form = $(this).serialize();
$('#list-items').load(url, form);
return false; // prevent the default submit action
})
</script>
Но он просто перезагружает страницу, ничего не принося, и контроллер списка никогда не попадает.
Список действий
public ActionResult List(PIMPSearchViewModel search)
{
var model = new PIMPListViewModel();
using (var context = new dbBEMIEntities())
{
//TODO:
model.Pimps = context.tbPIMPs.Where(p => p.id_pimp == search.Id &&
p.service_type.Equals(search.SelectedServiceType, StringComparison.InvariantCultureIgnoreCase) &&
p.status.Equals(search.SelectedStatus, StringComparison.InvariantCultureIgnoreCase)).ToList();
foreach (var item in model.Pimps)
{
item.status = context.tbParams.Where(k => k.key_complement == item.status).Select(k => k.param_value).FirstOrDefault();
}
}
return PartialView(model);
}
Нет, это всего лишь один из «ответов», которые я нашел при просмотре переполнения стека. Спасибо!





Если нет особой причины для отправки с помощью jquery, я бы использовал встроенный помощник Ajax.BeginForm.
Во-первых, измените объявление формы, чтобы использовать ajax (обратите внимание на изменение с Html.BeginForm на Ajax.BeginForm...):
@using (Ajax.BeginForm("List", "Home",
new AjaxOptions
{
InsertionMode = InsertionMode.Replace,
HttpMethod = "POST",
UpdateTargetId = "search-results"
}))
{
@Html.EditorFor(model => model.Id, new { htmlAttributes = new { @class = "form-control", @id = "Id", @type = "text" } })
@Html.EditorFor(model => model.Name, new { htmlAttributes = new { @class = "form-control", @id = "Name", @type = "text" } })
<input type = "submit" value = "Search" />
}
Итак, что здесь происходит, так это то, что он будет использовать ajax для отправки формы, а затем, когда результат будет возвращен, мы говорим ему обновить div с идентификатором «результаты поиска», заменив этот div результатами. В этом случае результаты будут вашим частичным представлением. Также обратите внимание, что мы указываем контроллер и действие в параметрах формы.
Затем измените div для результатов поиска. Здесь нет необходимости в вызове рендеринга, потому что он нам не нужен до завершения поиска:
<div class = "row">
<div id = "search-results"></div>
</div>
Обратите внимание, что идентификатор div соответствует параметрам ajax UpdateTargetId.
Затем в методе пост-контроллера я бы сделал только одно изменение, чтобы указать имя частичного представления в возврате. Не уверен, что это необходимо на 100%, но я много раз сталкивался с проблемами, если не делал этого:
[HttpPost]
public ActionResult List(Student model)
{
// Do stuff
return PartialView("_myPartial", model);
}
Последнее, что нужно сделать, это убедиться, что у вас установлен пакет nuget Microsoft.jQuery.Unobtrusive.Ajax и скрипт включен в пакет. Это нужно сделать ajaxy, иначе частичный вид будет возвращен как полная страница.
ОБНОВИТЬ:
Как добавить скрипт в бандл. Просто добавьте его в пакет jquery. Откройте файл BundleConfig.cs в папке App_Start. Найдите пакет jQuery, который обычно находится первым:
bundles.Add(new ScriptBundle("~/bundles/jquery").Include(
"~/Scripts/jquery-{version}.js"));
И добавьте новую строку, чтобы включить ненавязчивый ajax, чтобы это выглядело так:
bundles.Add(new ScriptBundle("~/bundles/jquery").Include(
"~/Scripts/jquery-{version}.js",
"~/Scripts/jquery.unobtrusive-ajax.min.js"));
Привет, BattlFrog. Я очень рад попробовать вашу альтернативу, но не могли бы вы помочь мне собрать Unobtrusive ajax? Мой текущий код — это bundles.Add(new ScriptBundle("~/bundles/jqueryunobtrusive-ajax").Include("~/Scripts/jquery.unobtrusive-ajax*")); первый параметр я только что назвал так, как я думал, это правильно? Спасибо
@Dwight Дуайт, я добавил в ответ инструкции по комплектации.
Привет Дуайт. Есть ли причина, по которой вы должны использовать этот скрипт jquery для отправки? Если нет, я бы использовал встроенную форму MVC Ajax. Пример для подражания.