I have a page that contains 3 divisions such as General, Attendee Information and Customized Questions (Partial view). The Customized questions will display a list of questions (textbox) along with the answer(dropdownlist) , which contains an edit button to modify the answer field in the dropdownlist. Now, when the edit button was clicked, a pop-up window will appear to modify the answer field, once the user clicked the save button the modified answer should reflects in the dropdownlist. I already created a partial view for Customized Questions but still the answer value didn't reflect the changes in the dropdownlist. Any sample codes or ideas?
Controller
[HttpPost]
public ActionResult UpdateAnswers(string answers, string question, string controlid, int eventid)
{
var replacetext=string.Empty;
if (answers.Length>0)
replacetext = answers.Replace("\n", ",");
_service.UpdateAnswers(eventid, replacetext, controlid);
var eventdetails = _service.GeteventByID(eventid);
return PartialView( "CustomizedQuestions", eventdetails);
}
Partial View
#using EM.Website.Helpers
#model EM.Model.tbl_SBAem_Event
#{
var dropdownList = new List<KeyValuePair<int, string>> {new KeyValuePair<int, string>(0, "Required"), new KeyValuePair<int, string>(1, "Optional"), new KeyValuePair<int, string>(2, "Hidden")};
var selectList = new SelectList(dropdownList, "key", "value", 0);
}
#using (Html.BeginForm())
{
#Html.ValidationSummary(true)
<table class="table-customized-question">
<tr>
<th class="td-customized-question-row"></th>
<th class="td-customized-question-row">Question Label</th>
<th class="td-customized-question-row">Display Mode</th>
<th class="td-customized-question-row">Answer Field</th>
<th class="td-customized-question-row">Edit Choices</th>
</tr>
<tr>
<td class="td-customized-question-firstrow">#1</td>
<td class="td-customized-question-row">#Html.EditorFor(model => model.EM_opt1Name)</td>
<td class="td-customized-question-row">#Html.DropDownListFor(model => model.EM_reqOpt1, selectList)</td>
<td class="td-customized-question-row">#Html.DropDownListFor(model => model.EM_opt1Values, #Html.SplitText(Model.EM_opt1Values, ','), new { #class = "dropdownlist-width" })</td>
<td>#Html.ActionImage("CustomizedQuestion", new { eventID = Model.EventMngID, question = Model.EM_opt1Name }, "~/Content/Images/edit.jpg", "Edit", new { #class = "editButton", title = Model.EM_opt1Name, answers = Model.EM_opt1Values, id = "EM_opt1Values", eventID = Model.EventMngID })</td>
</tr>
<tr>
<td class="td-customized-question-firstrow">#2</td>
<td class="td-customized-question-row">#Html.EditorFor(model => model.EM_opt2Name)</td>
<td class="td-customized-question-row">#Html.DropDownListFor(model => model.EM_reqOpt2, selectList)</td>
<td>#Html.ActionImage("CustomizedQuestion", new { eventID = Model.EventMngID, question = Model.EM_opt2Name }, "~/Content/Images/edit.jpg", "Edit", new { #class = "editButton", title = Model.EM_opt2Name, answers = Model.EM_opt2Values, id = "EM_opt2Values", eventID = Model.EventMngID })</td>
</tr>
<tr>
<td class="td-customized-question-firstrow">#3</td>
<td class="td-customized-question-row">#Html.EditorFor(model => model.EM_opt3Name)</td>
<td class="td-customized-question-row">#Html.DropDownListFor(model => model.EM_reqOpt3, selectList)</td>
<td class="td-customized-question-row">#Html.DropDownListFor(model => model.EM_opt3Values, #Html.SplitText(Model.EM_opt3Values, ','), new { #class = "dropdownlist-width" })</td>
<td>#Html.ActionImage("CustomizedQuestion", new { eventID = Model.EventMngID, question = Model.EM_opt3Name }, "~/Content/Images/edit.jpg", "Edit", new { #class = "editButton", title = Model.EM_opt3Name, answers = Model.EM_opt3Values, id = "EM_opt3Values", eventID = Model.EventMngID })</td>
</tr>
<tr>
<td class="td-customized-question-firstrow">#4</td>
<td class="td-customized-question-row">#Html.EditorFor(model => model.EM_opt4Name)</td>
<td class="td-customized-question-row">#Html.DropDownListFor(model => model.EM_reqOpt4, selectList)</td>
<td class="td-customized-question-row">#Html.DropDownListFor(model => model.EM_opt4Values, #Html.SplitText(Model.EM_opt4Values, ','), new { #class = "dropdownlist-width" })</td>
<td>#Html.ActionImage("CustomizedQuestion", new { eventID = Model.EventMngID, question = Model.EM_opt4Name }, "~/Content/Images/edit.jpg", "Edit", new { #class = "editButton", title = Model.EM_opt4Name, answers = Model.EM_opt4Values, id = "EM_opt4Values", eventID = Model.EventMngID })</td>
</tr>
<tr>
<td class="td-customized-question-firstrow">#5</td>
<td class="td-customized-question-row">#Html.EditorFor(model => model.EM_opt5Name)</td>
<td class="td-customized-question-row">#Html.DropDownListFor(model => model.EM_reqOpt5, selectList)</td>
<td class="td-customized-question-row">#Html.DropDownListFor(model => model.EM_opt5Values, #Html.SplitText(Model.EM_opt5Values, ','), new { #class = "dropdownlist-width" })</td>
<td>#Html.ActionImage("CustomizedQuestion", new { eventID = Model.EventMngID, question = Model.EM_opt5Name }, "~/Content/Images/edit.jpg", "Edit", new { #class = "editButton", title = Model.EM_opt5Name, answers = Model.EM_opt5Values, id = "EM_opt5Values", eventID = Model.EventMngID })</td>
</tr>
<tr>
<td class="td-customized-question-firstrow">#6</td>
<td class="td-customized-question-row">#Html.EditorFor(model => model.EM_opt6Name)</td>
<td class="td-customized-question-row">#Html.DropDownListFor(model => model.EM_reqOpt6, selectList)</td>
<td class="td-customized-question-row">#Html.DropDownListFor(model => model.EM_opt6Values, #Html.SplitText(Model.EM_opt6Values, ','), new { #class = "dropdownlist-width" })</td>
<td>#Html.ActionImage("CustomizedQuestion", new { eventID = Model.EventMngID, question = Model.EM_opt6Name }, "~/Content/Images/edit.jpg", "Edit", new { #class = "editButton", title = Model.EM_opt6Name, answers = Model.EM_opt6Values, id = "EM_opt6Values", eventID = Model.EventMngID })</td>
</tr>
</table>
}
Jquery-Ajax
$(".editButton").live("click", function (e) {
e.preventDefault();
var $title = $(this).attr("title");
var $answers = $(this).attr("answers");
var $controlid = $(this).attr("id");
var $eventId = $(this).attr("eventID");
dropdownlist($controlid, $title, $answers, $eventId);
});
function dropdownlist(controlid, title, answer, eventid) {
var $answersreplaced = answer.replace(/\,/g, " \r");
var $deleteDialog = $('<div><textarea id="answerlist" rows="10" cols="50">' + $answersreplaced + '</textarea><div><div style="font-size:9px">(To change back to an open answer field, delete all choices above and save)</div>');
$deleteDialog.dialog({
resizable: false,
height: 280,
width: 350,
title: title + " - Edit Choices",
modal: true,
buttons: {
"Save": function () {
$.ajax({
url: '#Url.Action("UpdateAnswers")',
type: 'POST',
dataType: 'html',
context: $(this),
data: {
answers: $("#answerlist").val(),
question: title,
controlid: controlid,
eventid: eventid
},
success: function (result) {
$(this).dialog("close");
alert(result);
$("#"+controlid+"").html(data);
},
error: function () {
//xhr, ajaxOptions, thrownError
alert('there was a problem saving the new answers, please try again');
}
});
},
Cancel: function () {
$(this).dialog("close");
}
}
});
};
Do my approach is correct?
Yes, your approach is correct. You could for example use jQuery UI dialog to implement the popup and editing part. The idea is to use AJAX in order to avoid refreshing the whole page but only the portion you are interested in. So the partial that will be shown in the modal dialog will contain a form that will be submitted to a controller action using AJAX and the server will return the partial view with the new information about the questions.
You must use
$.ajax({
type: "POST",
url: '#Url.Action("action", "controller")',
data: "{... parameterd}",
contentType: "application/json; charset=utf-8",
success: function (data) {
.. $("#yourDivID").html(data);
}
});
#using (Ajax.BeginForm("action", "controller", ajaxOptions)) , not
#using (Html.BeginForm())
Related
I am having partial success searching / grouping data through a viewmodel:
Partial Success:
URL Value
If I search on "B"
https://localhost:7207/Class01Name/Index2?String02NameSelected=B&SearchString=
Problem:
Not filtering data...simply changes pull down menu back to "All," displaying all data. Data not filtered.
**Question:
**
What in the code has to be changed to have the data filtered successfully?
Question is based on Tutorial at:
https://learn.microsoft.com/en-us/aspnet/core/tutorials/first-mvc-app/search?view=aspnetcore-6.0
Model
using System.ComponentModel.DataAnnotations; // Date Format
namespace Project01Name.Models
{
public class Class01Name
{
public int Id { get; set; }
public string? String01Name { get; set; }
public string? String02Name { get; set; }
public int? Int01Name { get; set; }
public bool? Bool01Name { get; set; }
[DataType(DataType.Date)]
public DateTime? DateTime01Name { get; set; }
}
}
**
View Model
**
using Microsoft.AspNetCore.Mvc.Rendering;
using System.Collections.Generic;
namespace Project01Name.Models.ViewModelsName
{
public class SearchByGroupName
{
public List<Class01Name>? Class01NameList { get; set; } // A list of movies.
public SelectList? String02NameSelection { get; set; } // A SelectList containing the list of genres. This allows the user to select a genre from the list.
public string? String02NameSelected { get; set; } // MovieGenre, which contains the selected genre.
public string? SearchString { get; set; } // SearchString, which contains the text users enter in the search text box.
}
}
Controller Action Method
// GET: String01Names
public async Task<IActionResult> Index2(string class01NameGroup, string searchString)
{
// Use LINQ to get list of genres.
IQueryable<string> string02NameQuery = from m in _context.Class01Name
orderby m.String02Name
select m.String02Name;
var selectVariable = from m in _context.Class01Name
select m;
if (!string.IsNullOrEmpty(searchString))
{
selectVariable = selectVariable.Where(s => s.String01Name!.Contains(searchString));
}
if (!string.IsNullOrEmpty(class01NameGroup))
{
selectVariable = selectVariable.Where(x => x.String02Name == class01NameGroup);
}
var string02NameVM = new SearchByGroupName
{
String02NameSelection = new SelectList(await string02NameQuery.Distinct().ToListAsync()),
Class01NameList = await selectVariable.ToListAsync()
};
return View(string02NameVM);
}
View
#model Project01Name.Models.ViewModelsName.SearchByGroupName
#{
ViewData["Title"] = "Index";
}
<h1>Index</h1>
<p>
<a asp-action="Create">Create New</a>
</p>
<form asp-action="Index2" method="get">
<div class="form-actions no-color">
<p>
<select asp-for="String02NameSelected" asp-items="Model.String02NameSelection"> <option value="">All</option></select>
Title: <input type="text" asp-for="SearchString" />
<input type="submit" value="Filter" />
#*<input type="submit" value="Search" class="btn btn-default" /> |
<a asp-action="Index">Back to Full List</a> *#
</p>
</div>
</form>
<table class="table">
<thead>
<tr>
<th>
#Html.DisplayNameFor(model => model.Class01NameList[0].String01Name)
</th>
<th>
#Html.DisplayNameFor(model => model.Class01NameList[0].String02Name)
</th>
<th>
#Html.DisplayNameFor(model => model.Class01NameList[0].Int01Name)
</th>
<th>
#Html.DisplayNameFor(model => model.Class01NameList[0].DateTime01Name)
</th>
<th></th>
</tr>
</thead>
<tbody>
#foreach (var item in Model.Class01NameList)
{
<tr>
<td>
#Html.DisplayFor(modelItem => item.String01Name)
</td>
<td>
#Html.DisplayFor(modelItem => item.String02Name)
</td>
<td>
#Html.DisplayFor(modelItem => item.Int01Name)
</td>
<td>
#Html.DisplayFor(modelItem => item.DateTime01Name)
</td>
<td>
<a asp-action="Edit" asp-route-id="#item.Id">Edit</a> |
<a asp-action="Details" asp-route-id="#item.Id">Details</a> |
<a asp-action="Delete" asp-route-id="#item.Id">Delete</a>
</td>
</tr>
}
</tbody>
</table>
Partial Success:
URL Value
If I search on "B"
https://localhost:7207/Class01Name/Index2?String02NameSelected=B&SearchString=
Problem:
Not filtering data...simply changes pull down menu back to "All," displaying all data. Data not filtered.
**Question:
**
What in the code has to be changed to have the data filtered successfully?
Question is based on Tutorial at:
https://learn.microsoft.com/en-us/aspnet/core/tutorials/first-mvc-app/search?view=aspnetcore-6.0
Not filtering data...simply changes pull down menu back to "All,"
displaying all data. Data not filtered.
**Question: ** What in the code has to be changed to have the data filtered successfully?
Well, seems you wanted to implement searching functionality in way, so that you can filter with the dropdown and search box and finally if you select All as dropdown value you want to load all the list without any filter and shorting means the full list which comes at first view.
If so, you need to use javascript for your dropdown change event as cshtml doesn't deal with change event. In addition, as you are using asp.net core MVC which would return HTML View altough, we need json data for Ajax reponse but we are would bee getting HTML View. So Ajax success Function will through an error where we would use filter with All parameter.
Modification Required:
Javascript:
#section scripts {
<script src="https://ajax.aspnetcdn.com/ajax/jQuery/jquery-3.2.1.min.js"></script>
<script src="https://cdn.datatables.net/1.11.3/js/jquery.dataTables.min.js"></script>
<script>
$(document).ready(function () {
$("#allId").change(function () {
alert("Click");
var allId = $('#allId').val();
console.log(allId);
if (allId == "All") {
alert("Alert");
$.ajax({
url: 'http://localhost:5094/Search/Index2',
type: 'GET',
dataType: 'json',
data: { String02NameSelected: "All", searchString: "" },
success: function (response) {
},
error: function () {
window.location.href = "#Url.Action("Index2", "Search")?String02NameSelected=All&SearchString=";
}
});
}
});
});
</script>
}
Note:
As you can see, in success function we are doing nothing, because it will always throuh an error because we are not returning json. Thus, we will work in error section. indow.location.href = "#Url.Action("Index2", "Search")?String02NameSelected=All&SearchString=";. Here, for your understanding, we will call this function when we select All as our dropdown value in that scenario, we will pass All and nothing , nothing will convert into null and all will be our search key.
Modify Your Existing View:
In your existing view, replace blow dropdown code snippet , means the select items
<select asp-for="String02NameSelected" id="allId" asp-items="Model.String02NameSelection"> <option value="All">All</option></select>
Note: If you notice I hav introduced a id id="allId" which will be using on dropdown change event.
Controller:
public async Task<IActionResult> Index2(string String02NameSelected, string searchString)
{
if (String02NameSelected == "All" && searchString == null)
{
var dataWithoutfileter = new SearchByGroupName();
dataWithoutfileter.String02NameSelection = new SelectList(String02NameSelectionList, "Text", "Value");
dataWithoutfileter.Class01NameList = listOfClass01Name;
return View(dataWithoutfileter);
}
if (!String.IsNullOrEmpty(String02NameSelected) && String02NameSelected !="All")
{
var objOfClass = new SearchByGroupName();
var string02NameQuery = listOfClass01Name.Where(m => m.String01Name.ToLower().Contains(String02NameSelected.ToLower()) || m.String02Name.ToLower().Contains(String02NameSelected.ToLower()));
objOfClass.Class01NameList = string02NameQuery.ToList();
objOfClass.String02NameSelection = new SelectList(String02NameSelectionList, "Text", "Value");
return View(objOfClass);
}
if (!String.IsNullOrEmpty(searchString))
{
var objOfClass = new SearchByGroupName();
var string02NameQuery = listOfClass01Name.Where(m => m.String01Name.ToLower().Contains(searchString.ToLower()) || m.String02Name.ToLower().Contains(searchString.ToLower()));
objOfClass.Class01NameList = string02NameQuery.ToList();
objOfClass.String02NameSelection = new SelectList(String02NameSelectionList, "Text", "Value");
return View(objOfClass);
}
//First loading
var objSearchByGroupName = new SearchByGroupName();
objSearchByGroupName.String02NameSelection = new SelectList(String02NameSelectionList, "Text", "Value");
objSearchByGroupName.Class01NameList = listOfClass01Name;
return View(objSearchByGroupName);
}
}
Complete Demo:
Full Controller With Seed Model Class Value:
public class SearchController : Controller
{
public static List<Class01Name> listOfClass01Name = new List<Class01Name>()
{
new Class01Name() { Id =101, String01Name ="Titanic",String02Name = "Romantic", Int01Name =01, Bool01Name = false, DateTime01Name = new DateTime(2023-01-15) },
new Class01Name() { Id =102, String01Name ="Forest gump",String02Name = "Motivational", Int01Name =02, Bool01Name = true, DateTime01Name = new DateTime(2023-01-12) },
new Class01Name() { Id =103, String01Name ="Spider Man",String02Name = "Action", Int01Name =03, Bool01Name = false, DateTime01Name = new DateTime(2023-01-10) },
new Class01Name() { Id =104, String01Name ="Harry Potter",String02Name = "Suspense", Int01Name =04, Bool01Name = true, DateTime01Name = new DateTime(2023-01-13)},
};
public List<SelectListItem> String02NameSelectionList = new List<SelectListItem>()
{
new SelectListItem { Text = "Motivational", Value = "Motivational" },
new SelectListItem { Text = "Romantic", Value = "Romantic" },
new SelectListItem { Text = "Action", Value = "Action" },
new SelectListItem { Text = "Comedy", Value = "Comedy" }
};
public async Task<IActionResult> Index2(string String02NameSelected, string searchString)
{
if (String02NameSelected == "All" && searchString == null)
{
var dataWithoutfileter = new SearchByGroupName();
dataWithoutfileter.String02NameSelection = new SelectList(String02NameSelectionList, "Text", "Value");
dataWithoutfileter.Class01NameList = listOfClass01Name;
return View(dataWithoutfileter);
}
if (!String.IsNullOrEmpty(String02NameSelected) && String02NameSelected !="All")
{
var objOfClass = new SearchByGroupName();
var string02NameQuery = listOfClass01Name.Where(m => m.String01Name.ToLower().Contains(String02NameSelected.ToLower()) || m.String02Name.ToLower().Contains(String02NameSelected.ToLower()));
objOfClass.Class01NameList = string02NameQuery.ToList();
objOfClass.String02NameSelection = new SelectList(String02NameSelectionList, "Text", "Value");
return View(objOfClass);
}
if (!String.IsNullOrEmpty(searchString))
{
var objOfClass = new SearchByGroupName();
var string02NameQuery = listOfClass01Name.Where(m => m.String01Name.ToLower().Contains(searchString.ToLower()) || m.String02Name.ToLower().Contains(searchString.ToLower()));
objOfClass.Class01NameList = string02NameQuery.ToList();
objOfClass.String02NameSelection = new SelectList(String02NameSelectionList, "Text", "Value");
return View(objOfClass);
}
//First loading
var objSearchByGroupName = new SearchByGroupName();
objSearchByGroupName.String02NameSelection = new SelectList(String02NameSelectionList, "Text", "Value");
objSearchByGroupName.Class01NameList = listOfClass01Name;
return View(objSearchByGroupName);
}
}
Full View:
#model DotNet6MVCWebApp.Controllers.SearchByGroupName
#{
ViewData["Title"] = "Index";
}
<form asp-action="Index2" method="get">
<div class="form-actions no-color">
<p>
<select asp-for="String02NameSelected" id="allId" asp-items="Model.String02NameSelection"> <option value="All">All</option></select>
Title: <input type="text" asp-for="SearchString" />
<input type="submit" name="searchString" />
</p>
</div>
</form>
<table class="table">
<thead>
<tr>
<th>
#Html.DisplayNameFor(model => model.Class01NameList[0].String01Name)
</th>
<th>
#Html.DisplayNameFor(model => model.Class01NameList[0].String02Name)
</th>
<th>
#Html.DisplayNameFor(model => model.Class01NameList[0].Int01Name)
</th>
<th>
#Html.DisplayNameFor(model => model.Class01NameList[0].DateTime01Name)
</th>
<th></th>
</tr>
</thead>
<tbody>
#foreach (var item in Model.Class01NameList)
{
<tr>
<td>
#Html.DisplayFor(modelItem => item.String01Name)
</td>
<td>
#Html.DisplayFor(modelItem => item.String02Name)
</td>
<td>
#Html.DisplayFor(modelItem => item.Int01Name)
</td>
<td>
#Html.DisplayFor(modelItem => item.DateTime01Name)
</td>
<td>
<a asp-action="Edit" asp-route-id="#item.Id">Edit</a> |
<a asp-action="Details" asp-route-id="#item.Id">Details</a> |
<a asp-action="Delete" asp-route-id="#item.Id">Delete</a>
</td>
</tr>
}
</tbody>
</table>
#section scripts {
<script src="https://ajax.aspnetcdn.com/ajax/jQuery/jquery-3.2.1.min.js"></script>
<script src="https://cdn.datatables.net/1.11.3/js/jquery.dataTables.min.js"></script>
<script>
$(document).ready(function () {
$("#allId").change(function () {
alert("Click");
var allId = $('#allId').val();
console.log(allId);
if (allId == "All") {
alert("Alert");
$.ajax({
url: 'http://localhost:5094/Search/Index2',
type: 'GET',
dataType: 'json',
data: { String02NameSelected: "All", searchString: "" },
success: function (response) {
},
error: function () {
window.location.href = "#Url.Action("Index2", "Search")?String02NameSelected=All&SearchString=";
}
});
}
});
});
</script>
}
Output:
I’m using BeginForm inside of a child view. When I submit the form I’m still on the parent view but the child view goes away. I would like for the information to be submitted but the form to remain until the user wants to load another partial view or move away from the page entirely. Is there a way to prevent the page from disappearing upon submit? Here’s what my BeginForm looks like:
using (Html.BeginForm("Action", "Controller", new { fromTeacherPage = true, searchTeacher = instructorName, selectedDepartment = Model.Assignments.FirstOrDefault().departmentNumber, id = Model.Assignments.FirstOrDefault().InstructorId, strCategoryName = #ViewBag.categoryname }, FormMethod.Post, new { #name = "formName", #class = "nameOfClass" }))
{
//code for form here
<button id="submitButton" class="submitButton">Submit</button><br />
}
UPDATE:
<script type="text/javascript">
$(document).ready(function () {
$("#datep").datepicker({ showOn: "both", buttonText: "Select Date", changeMonth: true, changeYear: true, yearRange: "-2:+2", showOtherMonths: true, onSelect: function (date, datepickder) {
var sltdDate = { selectedDate: date };
$.ajax({
type: "GET",
url: "/Schedule/GetSchedule",
data: sltdDate,
datatype: "html",
success: function (data) {
$("#returnedData").html(data);
$("#returnedData #dateContainer").remove();
$("<button>Hide</button>").appendTo("#homeworkUpdateId-0")
}
});
}
});
});
</script>
#{
int? intTeacherID = Convert.ToInt32(HttpContext.Current.Session["intTeacherId"]);
string instructorName = (from x in Model.Enrollments where x.InstructorId == intTeacherID select x.InstructorFullName).FirstOrDefault();
}
<div id="dateContainer">
<label for ="datep">Date: </label><input id="datep" />
</div>
<div id="returnedData">
#if (Model.Assignments != null)
{
using (Html.BeginForm("Action", "Controller", new { fromTeacherPage = true, searchTeacher = instructorName, selectedDepartment = Model.Assignments.FirstOrDefault().departmentNumber, id = Model.Assignments.FirstOrDefault().teacherId, strCategoryName = #ViewBag.categoryname }, FormMethod.Post, new { #name = "formName", #class = "submitAttendance" }))
{
<table>
<tr>
<th>
Grade
</th>
<th>
Attendance
</th>
<th>
Clas Day
</th>
<th>
Assignment Type
</th>
<th>
Overall Grade
</th>
</tr>
#foreach (var assignment in Model.Assignments.Select((x, i) => new { Data = x, Index = i }))
{
int asgnIndex = assignment.Index;
<tr id="rowId+#asgnIndex">
<td>
<div id="homeworkUpdateId-#asgnIndex">
#Html.TextBox("HomeworkGrade", assignment.Data.HomeworkGrade.ToString(), new { style = "width:55px; text-align: center" })
</div>
</td>
</table>
<button id="submitButton" class="submitButton">Submit </button><br />
}
}
</div>
You are using
using(Html.BeginForm()){}
this will refresh the whole page if you only want to reload some section inside your view you have to use
using (Ajax.BeginForm("Action", "Controller", null, new AjaxOptions {UpdateTargetId = "divToUpdate", InsertionMode = InsertionMode.Replace, HttpMethod = "GET"}, new {id = "someIdFOrm"}))
I have a Ajax Jquery function:
function UpdateValue() {
$(document.body).on("change",".quantity", function () {
var ProID = $(this).attr("data");
var Quantity = $(this).val();
$.ajax({
type: "GET", url: "/Cart/UpdateValue",
data: { ProID: ProID, quantity: Quantity },
success: function (data) {
$("#cartbox").html(data);
}
}
);
$.ajaxSetup({
cache: false
});
});
}
call UpdateValue in Cart Controller:
public PartialViewResult UpdateValue(Cart cart,int ProID, int quantity)
{
List<SelectListItem> items = new List<SelectListItem>();
for (int i = 1; i <= 10; i++)
{
items.Add(new SelectListItem { Text = i.ToString(),
Value = i.ToString() });
}
ViewBag.Items = items;
Product product = repository.Products.FirstOrDefault(p => p.ProductID
== ProID);
if (product != null)
{
cart.UpdateItem(product, quantity);
}
CartIndexViewModel ptview = new CartIndexViewModel { Cart = cart,
ReturnUrl = "/" };
return PartialView(ptview);
}
When the ajax function success, it returns UpdateValue View. But the Dropdown List always changes the same in each row. How can i pass the selected value from the Index View after ajax update?
Here is my UpdateValue View Code:
<table id="cartbox">
<thead>
<tr>
<th>Tên hàng</th>
<th>Số lượng</th>
<th>Đơn giá</th>
<th colspan="2" style="width:70px">Thành tiền</th>
</tr>
</thead>
<tbody>
#foreach (var line in Model.Cart.Lines)
{
<tr>
<td>#line.Product.Name
</td>
<td>#Html.DropDownList("Quantity", new SelectList(ViewBag.Items as System.Collections.IList, "Value", "Text", line.Quantity), new { data = line.Product.ProductID, #class = "quantity" })</td>
<td style="color:#3A9504;margin-left:3px">#string.Format("{0:00,0 VNĐ}", line.Product.Price)</td>
<td>#string.Format("{0:00,0 VNĐ}", (line.Quantity * line.Product.Price))</td>
<td align="center" style="width:10px"><img src="#Url.Content("~/Content/Images/delete.png")" style="padding-right:10px" /></td>
</tr>
}
</tbody>
<tfoot>
<tr style="border-top-style:solid;border-top-color:#DFDFDF;border-top-width:1px;">
<td colspan="3" align="right" style="border-right-color:#808080;border-right-style:solid;border-right-width:1px;text-align:right"><b>Tổng tiền:</b></td>
<td style="text-align: center"><b>#string.Format("{0:00,0 VNĐ}", Model.Cart.ComputeTotalValue())</b></td>
<td></td>
</tr>
</tfoot>
</table>
If I understand you correctly then your problem is that after updating the data in the dropdown list you lose the selection in that dropdown list?
If so then you would need to add this to your success handler in JavaScript:
success: function (data) {
$("#cartbox").html(data);
$("#cartbox").find(".quantity").val(Quantity);
}
I have a partial view that has to display records on the change of dropdown. The values are coming correctly but it is not being displayed in the tex boxes. Please help. THe code of my partial view looks like below
#using (Ajax.BeginForm("W2State", new AjaxOptions() { UpdateTargetId = "model", OnSuccess = "w2Updated", InsertionMode = InsertionMode.Replace, HttpMethod = "Post" } ))
{
<fieldset id="currencyView" class="detailView">
<table>
<tr>
<td style="width: 100px;">Select Agency </td>
<td>
#*#Html.DropDownListFor(model => model.ReportingAgencies, new SelectList(Model.ReportingAgencies, "SelectedAgency.AgencyGuid", "SelectedAgency.Name"), new { id = "dropDownReportAgencies" })*#
#Html.DropDownListFor(model => model.ReportingAgencies, new SelectList(Model.ReportingAgencies, "SelectedAgency.AgencyGuid", "SelectedAgency.Name"), "--Select An Agency--", new { id = "dropDownReportAgencies" })
</td>
</tr>
<tr class="seperator"></tr>
<tr class="seperator"></tr>
<tr>
<td style="width: 100px;">#Html.LabelFor(model => model.W2StateLocal.Wages)</td>
<td> #Html.TextBoxFor(model => model.W2StateLocal.Wages)</td>
</tr>
<tr>
<td style="width: 100px;">#Html.LabelFor(model => model.W2StateLocal.Tax)</td>
<td>#Html.TextBoxFor(model => model.W2StateLocal.Tax)</td>
</tr>
</table>
<div id="rightButtonControls">
#if (Model.IsEditable)
{
<button id="btnSave" value="save">Save</button>
}
</div>
</fieldset>
}
#Html.HiddenFor(model => model.CompanyId, new { id = "CompanyId" })
#Html.HiddenFor(model => model.EmployeeId, new { id = "EmployeeId" })
#Html.HiddenFor(model => model.FilingYear, new { id = "FilingYear" })
<script type="text/javascript">
$(document).ready(function () {
$("#divLoader").css('display', 'none');
$('#dropDownReportAgencies').change(function () {
var selectedAgency = $('#dropDownReportAgencies option:selected').val();
var CompanyId = $('#CompanyId').val();
var EmployeeId = $('#EmployeeId').val();
var FilingYear = $('#FilingYear').val();
var url = '#Url.Action("W2State", "W2Generation")';
$.get(url, { agencyId: selectedAgency, companyId: CompanyId, employeeId: EmployeeId, filingYear: FilingYear },
function (data) {
});
});
});
You want to get text from dropdown in mvc through jQuery...
Your code is right but just missing something.. You used
var selectedAgency = $('#dropDownReportAgencies option:selected').val();
but instead of 'val' you have to use 'text'.. it means
var selectedAgency = $("#dropDownReportAgencies option:selected").text();
Try this....
I have a partial view that has textfields in it and is bound to a List set up, so essentially there is a row of textfields that the user can add another row to or remove a row from. I build the view by looping through the list like this:
#model PricingRequestWebApp.Web.Models.PricingRequestModel
<div id="shiplocation-wrapper">
<table class="shipinfoprtable">
<thead>
<tr>
<th>#Html.LabelFor(m => m.ShippingLocationsModel[0].Address)<span class="formRed">*</span></th>
<th>#Html.LabelFor(m => m.ShippingLocationsModel[0].City)<span class="formRed">*</span></th>
<th>#Html.LabelFor(m => m.ShippingLocationsModel[0].State)<span class="formRed">*</span></th>
<th>#Html.LabelFor(m => m.ShippingLocationsModel[0].Zip)<span class="formRed">*</span></th>
<th>#Html.LabelFor(m => m.ShippingLocationsModel[0].PFreight)<span class="formRed">*</span></th>
<th>#Html.LabelFor(m => m.ShippingLocationsModel[0].FreightType)<span class="formRed">*</span></th>
<td><span class="link" id="addlocation" onclick="AddShippingLocation()">Add</span></td>
</tr>
</thead>
<tbody>
#for (int i = 0; i < Model.ShippingLocationsModel.Count; i++)
{
<tr>
<td>#Html.TextBoxFor(m => m.ShippingLocationsModel[i].Address, new { #style = "width: 200px" })</td>
<td>#Html.TextBoxFor(m => m.ShippingLocationsModel[i].City, new { #style = "width: 150px" })</td>
<td>#Html.TextBoxFor(m => m.ShippingLocationsModel[i].State, new { #size = 3 })</td>
<td>#Html.TextBoxFor(m => m.ShippingLocationsModel[i].Zip, new { #style = "width: 80px" })</td>
<td>#Html.TextBoxFor(m => m.ShippingLocationsModel[i].PFreight, new { #style = "width: 80px" })</td>
<td>#Html.TextBoxFor(m => m.ShippingLocationsModel[i].FreightType, new { #style = "width: 200px" })</td>
#if (Model.ShippingLocationsModel.Count > 1)
{
<td><span class="link" id="removelocation" onclick="RemoveShippingLocation(#i);">Remove</span></td>
}
</tr>
}
</tbody>
</table>
</div>
My controller methods look like so:
[HttpPost]
public ActionResult AddShippingLocation(PricingRequestModel model)
{
model.ShippingLocationsModel.Add(new ShippingLocationsModel());
return PartialView("shiplocationsPartial", model);
}
[HttpPost]
public ActionResult RemoveShippingLocation(PricingRequestModel model)
{
model.ShippingLocationsModel.RemoveAt(StaticItems.id);
return PartialView("shiplocationsPartial", model);
}
And my Jquery function that posts the data and returns the view:
function AddShippingLocation() {
$.ajax({
data: $('#shippinginfoform').serialize(),
type: "POST",
url: "/PricingRequest/AddShippingLocation",
success: function (response) {
$('#shiplocation-wrapper').html(response);
}
})
}
function RemoveShippingLocation(id) {
$.ajax({
data: { id: id },
type: "POST",
url: "/PricingRequest/SaveID",
complete: function () {
$.ajax({
data: $('#shippinginfoform').serialize(),
cache: false,
type: "POST",
url: "/PricingRequest/RemoveShippingLocation",
success: function (response) {
$('#shiplocation-wrapper').html(response);
}
})
}
})
}
Now, lets say I have 4 items created in the user view. I click on item 2 to remove it and it passes in i as an id. I then remove that from the model list and pass back the view with the updated model. I have debugged this at least 50 times now and the controller method looks exactly as it should and the data in the view as well. Inexplicably though the response on the ajax shows differently than what I'm seeing while debugging. Clicking on remove item 2 removes item 4. If I have 5 items, item 5 will be removed no matter what item I click to remove. It's always the last item that is removed. I know I must be missing something here but I can't see what. Any ideas? Thanks.
The problem with your code is that you are using sequential indexes for your collections and not recalculating those indexes when adding/removing elements leaving gaps which prevents the model binder from operating correctly. As an alternative you could use non-sequential indexes as illustrated in the following blog post.