Html.DropDownListFor and JavaScript Array - javascript

I've implemented Cascading Drop Down Lists on the Create View page of my MVC Asp.NET Application.
Unfortunately, I am having issues with selecting a value that is located in the JavaScript Array. I need to bind the selected value for the use of one of my controllers.
Right now my List populates, but I have no way to select it. Is there a way to move the counties[i] array from my JavaScript to the #Html.DropDownListFor() helper?
Thanks!
JavaScript:
<script src="#Url.Content("~/Scripts/jquery-1.10.2.min.js")"
type="text/javascript"></script>
<script language="javascript" type="text/javascript">
$(document).ready(function() {
$("#county").prop("disabled", true);
$("#StateLongName").change(function() {
if ($("#StateItems").val() != "Please select") {
var options = {};
options.url = "/County/GetCounties";
options.type = "POST";
options.data = JSON.stringify({ state: $("#StateLongName").val() });
options.dataType = "json";
options.contentType = "application/json";
options.success = function(counties) {
$("#county").empty();
for (var i = 0; i < counties.length; i++) {
$("#county").append("<option>" + counties[i] + "</option>");
}
$("#county").prop("disabled", false);
};
options.error = function() { alert("Error retrieving counties!"); };
$.ajax(options);
} else {
$("#county").empty();
$("#county").prop("disabled", true);
}
});
});
</script>
Controller:
//GET Counties for Cascading Dropdown List
public JsonResult GetCounties(string state)
{
var counties = db.countycigtaxes.Join(db.statecigtaxes,
cc => cc.stateid,
sc => sc.stateid,
(cc, sc) => new
{
cc,
sc
}).Where(co => co.sc.statefullname == state)
.Select(co => co.cc.countyfullname).ToList();
return Json(counties);
}
View Page:
<div class="form-group">
#Html.LabelFor(model => model.StateLongName, new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.DropDownListFor(m => m.StateLongName, Model.StateItems, "Please select")
#Html.ValidationMessageFor(model => model.StateLongName)
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.CountyLongName, new { #class = "control-label col-md-2" })
<div class="col-md-10">
#*#Html.DropDownListFor(m => m.CountyLongName, )*#
<select id="county"></select>
#Html.ValidationMessageFor(model => model.CountyLongName)
</div>
</div>

I assume you mean the the selected value of the property CountyLongName is not posting back when you submit the form. You have commented out this line
#Html.DropDownListFor(m => m.CountyLongName, )
and used
<select id="county"></select>
If you want the manual version (I do not recommend this), then you need to add a name attribute that matches the property name so it can be bound by the ModelBinder
<select name="CountyLongName" id="county"></select>
But it is better to use the helper and pass it an empty SelectList
Html.DropDownListFor(m => m.CountyLongName, Model.CountryNames)
where Model.CountryNames is a property in you view model that is initialised to an empty SelectList
Note also options.type = "POST"; should be "GET" and the whole AJAX could be simplified to
$.get('#Url.Action("GetCounties","Country")', { state: $('#StateLongName').val() }, function(countries) {...
and theToList() is not required in the JsonResult method

This should set the option selected for you.
$("#county option[value='" + counties[index] + "']").attr("selected", "selected");

Related

How can I populate a dropdownlist based on the selected value of another dropdownlist? MVC

I am currently trying to populate the values for a car's model based on the selected make in a dropdownlist. I am new to coding so I am not sure what my mistake is. The project doesn't give me any errors but no values are displayed when I selected the make.
This is my Partial View that I am adding into my Create View.
#model IgnitionHubPractice.Models.MakeModelDorpdownView
<div class="form-horizontal">
<div class="form-group">
#if (ViewBag.MakeList != null)
{
#Html.DropDownListFor(m => m.MakeID, ViewBag.MakeList as SelectList, "--Select Make--", new { #class = "form-control" })
}
</div>
<div class="form-group">
#Html.DropDownListFor(m => m.ModelID, new SelectList(" "), "--Select Model--", new { #class = "form-control" })
</div>
</div>
<script>
$(document).ready(function () {
$("#MakeID").change(function () {
$.get("/Cars/GetModelList",{ MakeID: $("MakeID").val() }, function (data) {
$("#ModelID").empty();
$.each(data, function (index, row) {
$("#ModelID").append("<option value ='" + row.ModelID + "' >" + row.Name + </option>")
});
});
})
});
</script>
This is my controller
public ActionResult Create([Bind(Include = "CarID,Year,Color,Mileage,Cost,MarketValue,BodyType,Drive,Notes,Available,VinNumber,CarLotID,ModelID")] Car car, [Bind(Include ="MakeID,Name")] Make make)
{
if (ModelState.IsValid)
{
db.Cars.Add(car);
db.SaveChanges();
return RedirectToAction("Index");
}
List<Make> MakeList = db.Makes.ToList();
ViewBag.MakeList = new SelectList(db.Makes, "MakeID", "Name", make.MakeID);
ViewBag.ModelID = new SelectList(db.Models, "ModelID", "Name", car.ModelID);
ViewBag.CarLotID = new SelectList(db.CarLots, "CarLotID", "LotName", car.CarLotID);
return View(car);
}
public JsonResult GetModelList(int MakeID)
{
db.Configuration.ProxyCreationEnabled = false;
List<Model> ModelList = db.Models.Where(x => x.MakeID == MakeID).ToList();
return Json(ModelList, JsonRequestBehavior.AllowGet);
}
Please help, thanks in advance.
In MVC you try to create a cascading drop down. So for easy understanding you can check the below link. It contanin detailed information for controller and View with Jquery part.
Please visit this link: Cascading Drop down List With MVC And AJAX

Replace text in values from dropdowns in razor statements

I have a HTML form with some dropdowns. I need the values of the selected item in the dropdowns to replace tags from another dropdown.
#Html.DropDownListFor(model => model.TrainID, new SelectList(Model.TrainItems, "Value", "Text"), htmlAttributes: new { id = "train" })
#Html.DropDownListFor(model => model.ReasonID, new SelectList(Model.ReasonItems, "Value", "Text"), htmlAttributes: new { id = "reason" })
#Html.DropDownListFor(model => model.MessageID, new SelectList(Model.MessageItems, "Value", "Text"), htmlAttributes: new { id = "message" })
I need the values of the train and the reason selected by the user to replace certain parts of the message item selected.
For example, the message selected would say: "Train # [NUM] has been cancelled due to [REASON]. We apologize for the inconvenience." And then it would dynamically populate the message with the selected values from the first two dropdowns into a textbox on the HTML form: "Train # 123 has been cancelled due to weather. We apologize for the inconvenience.":
#Html.EditorFor(model => model.AnnouncementText, new { htmlAttributes = new { id = "text" } })
I've tried to do this through javascript with no luck:
$(function () {
var str = document.getElementById("message").innerHTML;
var res = str.replace("[REASON]", model.ReasonName);
document.getElementById("text").innerHTML = res;
});
Clearly, the string.replace method isn't meant for razor statements and I'm wondering if there is a such a method or if I'm going about this the wrong way.
With a little help, I was able to find the answer that worked best for me. I was really close with my first attempt and with a few tweaks was able to get it.
$('#message').on('change', function () {
var selection = $.trim($("#message :selected").text()));
var str = document.getElementById("reason");
var reason = str.option[str.selectedIndex].text;
var res = selection.replace("[REASON]", reason);
$('#text').val(res);
});
Thank you to RajN for the help!

how to append a number of dropdowns on button click with each dropdown having different indexing in name attribute?

I am trying to append a number of dropdowns on Button click.These dropdowns should have proper indexing in its 'name' attribute.
This is the dropdown:-
<div id="dropdownDiv" style="display:none">
<div class="form-group">
#Html.LabelFor(model => model.PropertyInvestors, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.DropDownListFor(model => model.PropertyInvestors, (IEnumerable<SelectListItem>)#ViewBag.Investors, "Select Investor", htmlAttributes: new { #id = "dropdown",#name= "[#].PropertyInvestors", #class = "form-control",#onChange="dropdownChange()" })
#Html.ValidationMessageFor(model => model.PropertyInvestors, "", new { #class = "text-danger" })
</div>
</div>
</div>
This is the JS code that I am trying in order to clone the dropdown and replace its name attribute with desired indexing.
$('#addDropdown').click(function () {
var index = (new Date()).getTime();
var clone1 = $('#dropdownDiv').clone();
clone1.html($(clone1).html().replace(/\[#\]/g, '[' + index + ']'));
$('#field1').append(clone1.html());
});
Problem:- The dropdowns are being appended as they are clicked but their name attributes are same for all of the dropdowns produced due to which I cant postback the data to the controller.
While this problem can be solved by using dummy code and manipulating the Index no. by using JS, a good method would be to use Html.BeginCollectionItem() by creating a partial view for the dropdown and later making an ajax call to append the partial view to the main view. Refer to the answer HERE
You can replace ID and Name as follows:
$('#addDropdown').click(function () {
var index = (new Date()).getTime();
var clone1 = $('#dropdownDiv').clone();
$(clone1).find('select').attr("id", index);
$(clone1).find('select').attr("name", "PropertyInvestor[" + index +"]");
$('#field1').append(clone1.html());
});
JSFiddler: https://jsfiddle.net/qj24yybe/6/

How do I use ACE for TextAreaFor in ASP.NET MVC5 application?

I am trying to Get ACE editor for javaScript purpose but i am not able to post my Editor data when i am clicking Save button its show NULL value in DB.
but when i am using normal Textarea without ACE my data is saving properly.
This is My CSHTML code.
<div class="form-group row">
<div class="col-lg-11" id="JavaScriptEditor">
#Html.Label("JavaScript", new { #class = "control-label" })
#Html.TextAreaFor(x=>x.JavaScript,new {#class="JavaScript"})
#Html.ValidationMessageFor(model => model.JavaScript, "", new { #class = "text-danger" })
</div>
</div>
This is my JS Code:-
<script>
var editor = ace.edit("JavaScript");
editor.setTheme("ace/theme/terminal");
editor.getSession().setMode("ace/mode/javascript");
window.onload = function () {
$("form").submit(function () {
$(".JavaScript").val().editor.getSession().getValue();
})
};
</script>
This is My Controller Code:-
[HttpPost]
[ValidateInput(false)]
public ActionResult AddEdit(Article article, FormCollection formCollection)
{
article.CompanyId = OperatingUser.CompanyId;
if(string.IsNullOrWhiteSpace(article.Slug))
article.Slug = article.Name.GenerateSlug();
if (string.IsNullOrWhiteSpace(article.SlugKey))
article.SlugKey = SlugKey();
//bool isUnique = _articleService.IsSlugUnique(slug: article.Slug, articleId: article.Id);
//if (!isUnique)
// article.Slug = $"{article.Slug}-1";
article.CreatedById = OperatingUser.Id;
article.ModifiedById = OperatingUser.Id;
if (article.Tags != null && article.Tags.Any())
article.Tag = string.Join(",", article.Tags);
if (formCollection.GetValue("SubmitButton").AttemptedValue
.Equals("Save and Publish", StringComparison.OrdinalIgnoreCase))
article.IsPublished = true;
article.RoleIds = formCollection.GetValue("selectedRoles").AttemptedValue;
if (article.Id > 0)
{
article.ModifiedById = OperatingUser.Id;
_articleService.Update(article);
}
else
{
article = _articleService.Add(article);
}
return Json(new { RedirectUrl = Url.Action("Edit", "Content", new { area="cms", id = article.Id }) });
}
I am trying to Save This Property data in Db but i am not able to Save this Please Help me.

need help to resolve - Uncaught ReferenceError: data is not defined

I know there are many questions/tutorials for this subject, but cannot solve my problem.
I have to ask for your help. Second day cannot find out the solution to this simple problem.
I am trying as in this tutorial - http://www.c-sharpcorner.com/UploadFile/abhikumarvatsa/cascading-dropdownlist-in-Asp-Net-mvc/
That is working fine, but once i try from DB, i am getting error "Uncaught ReferenceError: data is not defined"
Here is my web page
#model testEmpty.Models.Address
#{
ViewBag.Title = "Create";
}
#Scripts.Render("~/bundles/jquery")
<script src="~/Scripts/myScripts/myScripts.js"></script>
<h2>Create</h2>
#using (Html.BeginForm())
{
#Html.AntiForgeryToken()
<div class="form-horizontal">
<h4>Address</h4>
<hr />
#Html.ValidationSummary(true, "", new { #class = "text-danger" })
<div class="form-group col-md-10">
#Html.Label("Zone")
#Html.DropDownList("ZoneId", ViewBag.ZoneName as SelectList, "--Select a Zone--", new { id = "ZoneId" })
#Html.ValidationMessage("Zone", "*")
</div>
<div class="form-group">
<div class="col-md-10">
#Html.Label("Districts of SZ")
<select id="DistrictSZ" name="DistrictSZ"></select>
</div>
</div>
<div class="form-group">
<div class="col-md-offset-2 col-md-10">
<input type="submit" value="Create" class="btn btn-default" />
</div>
</div>
</div>
}
<div>
#Html.ActionLink("Back to List", "Index")
</div>
#section Scripts {
#Scripts.Render("~/bundles/jqueryval")
}
Controller
private myContext db = new myContext();
// GET: Addresses
public ActionResult Index()
{
var zones = db.Addresses.Include(a => a.Zone);
ViewBag.ZoneName = new SelectList(zones, "Value", "Text");
return View(zones.ToList());
}
public JsonResult DistrictList(int id)
{
var district = from s in db.Districts
where s.ZoneId == id
select s;
return Json(new SelectList(district.ToArray(), "ZoneId", "Name"), JsonRequestBehavior.AllowGet);
}
Script
$(function () {
$('#ZoneId').change(function () {
$.getJSON('DistrictList/' + $('#ZoneId').val(), getDistricts (data));
});
});
function getDistricts(data) {
var items = '<option>Select a District</option>';
$.each(data, function (i, district) {
items += "<option value='" + district.Value + "'>" + district.Text + "</option>";
});
$('#DistrictSZ').html(items);
}
As i understand, my problem is with JSON. what am I doing wrong?
Firstly you do not need to return a SelectList (javascript knows nothing about a c# class)
public JsonResult DistrictList(int id)
{
var district = db.Districts.Where(d => d.ZoneId == id).Select(d => new
{
Value = d.ZoneId, // this look wrong - see note below
Text = d.Name
});
return Json(district, JsonRequestBehavior.AllowGet);
}
Then in your script
var url = '#Url.Action("DistrictList")'; // ensure your url's are properly generated
var districts = $('#DistrictSZ'); // cache it
$('#ZoneId').change(function () {
$.getJSON(url, { id: $(this).val() }, function (data) {
districts.empty(); // remove existing options
districts.append($('</option>').val('').text('Select a District'));
$.each(data, function (i, district) {
districts.append($('</option>').val(district.Value).text(district.Text));
});
});
});
In fact, since ZoneId is always the same, you could just return a collection of the Name values
var district = db.Districts.Where(d => d.ZoneId == id).Select(d => d.Name);
and
$('#ZoneId').change(function () {
var zoneID = $(this).val();
$.getJSON(url, { id: zoneID }, function(data) {
districts.empty(); // remove existing options
districts.append($('</option>').val('').text('Select a District'));
$.each(data, function (i, district) {
districts.append($('</option>').val(zoneID).text(district));
});
});
});
However your code is generating all options with the same value (ZoneId) which does not make much sense, so I suspect you really want to use another property of District - i.e. its Id (or DistrictId?) property.
You're passing the returned value of getDistricts to the callback variable of $.getJSON.
$.getJSON('DistrictList/' + $('#ZoneId').val(), getDistricts (data));
You need to pass the function reference like this
$.getJSON('DistrictList/' + $('#ZoneId').val(), getDistricts);
maybe you should handle your callback function with a anonymous function like this:
$.getJSON('DistrictList/' + $('#ZoneId').val(), success(data){
getDistricts(data);
})

Categories