I have the following on my controller:
string preferredLanguage = "fr-ca";
ViewData["Languages"] = new SelectList(languages, "Code", "Name", preferredLanguage);
On the view:
#Html.DropDownList("Languages", (SelectList)ViewData["Languages"], new { id = "Languages" });
My problem here is my dropdown is not setting the selected index of dropdown to the preferred language which is supposed to be French.
Note:
The values inside the languages:
1) Name = "English"
Code = "en-us"
2) Name = "French"
Code = "fr-ca"
And the dropdown shows two languages, English and French. English is set as selected index but what I want is French.
The reason I show the languages this way because this object are being retrieved from the database my a method and not by hardcoded. Thanks in advance!
I'd recommend using strongly-typed helpers bound to a model; something along these lines:
Model:
public class LanguageFormModel
{
public string SelectedLanguage { get; set; }
public SelectList Languages { get; set; }
}
Action:
[HttpGet]
public ActionResult YourActionName()
{
// replace this with however you're getting your language variable
var languages = new CollectionOfSomeSort();
var model = new LanguageFormModel()
{
SelectedLanguage = "fr-ca",
Languages = new SelectList(languages, "Code", "Name", "fr-ca")
};
return View(model);
}
View:
#model Your.Fully.Qualified.Namespace.LanguageFormModel
#Html.LabelFor(m => m.SelectedLanguage)
#Html.DropDownListFor(m => m.SelectedLanguage, Model.Languages, "Select one...")
I'm personally not a huge fan of using ViewData for anything other than simple messages, and even then I use TempData, since I'm mostly just showing confirmations/alerts.
This is working fine for me.
Dictionary<string, string> languages = new Dictionary<string, string>() { { "en-us", "English" }, { "fr-ca", "French" } };
ViewData["Languages"] = new SelectList(languages, "key", "value", "fr-ca");
IN VIEW
#Html.DropDownList("Language", ViewData["Languages"] as SelectList, new { id = "Languages" })
this is ok:
#Html.DropDownList("languages")
Related
I'm working with ASP.NET MVC 5 and Entity Framework 6, and I'm having a problem with the model selected value (only for decimal values) in my views.
That only happen when i'm getting data from database, if i try to submit the form, the value get back and is correctly selected.
This is my ViewModel
public class Regulacion
{
public IEnumerable<SelectListItem> ListaPorcentajePuntos
{
get
{
return new List<SelectListItem>
{
new SelectListItem { Text="0,625%" , Value = "0,625"},
new SelectListItem { Text="1%" , Value = "1"},
new SelectListItem { Text="1,25%", Value="1,25" },
new SelectListItem { Text="2,5%" , Value = "2,5"},
new SelectListItem { Text="5%" , Value = "5"},
};
}
}
public decimal? PorcentajePunto { get; set; }
//other stuff
public Regulacion(Reg reg)
{
PorcentajePunto = reg.PorcentajePunto;
}
}
And i'm using it in the view like this
#Html.DropDownListFor(x => x.PorcentajePunto, Model.ListaPorcentajePuntos, "Please select", new { #class = "form-control"})
I'm pretty sure, the problem become when i fetch the data from EF and decimal precision, because, when I'm debugging, the PorcentajePunto property stored 5.00 instead of 5, if i manually modify the property to 5 it works perfectly.
I read this question and try to use SelectList instead of SelectListItem but wasn't the solution
How can i deal with it?
Thanks!
EDIT
I'm fetching the Regulacion data like this
using(var db = new DBTrafosContext())
{
var a = db.Reg.FirstOrDefault();
if(a != null){
Regulacion newRegulacion = new Regulacion(a);
}
}
Hi I have Dropdown in Index page where user needs to select lists. Values are coming from Database. I took this dropdown value into session so I can carry this to Httppost.
Below is my code in Index page :
var activitydropdown = orderdata.uspApp_ActivityPageReportname(Convert.ToInt32(newid)).ToList();
List<SelectListItem> activitypage = new List<SelectListItem>();
if (activitydropdown != null && activitydropdown.Count > 0)
{
foreach (var activityresults in activitydropdown)
{
activitypage.Add(new SelectListItem
{
Text = activityresults.name,
Value = activityresults.id.ToString(),
});
}
}
ViewData["activitydropdown"] = activitypage;
Session["activitydropdown"] = activitypage;
And this is my code in view :
#using (Html.BeginForm("Index", "Automation", new { step = "2" }, FormMethod.Post, new { id = "frmIndex" }))
{
#Html.DropDownList("DrpaActivity", ViewData["activitydropdown"] as List<SelectListItem>, "All", new { style = "margin-left:694px;margin-bottom:20px;", onchange = "submit();" })
Now when user selects list from dropdown, i need to carry that text to my httpost index. Now in httpost index, in debug mode if i see this code :
var sessionlistautomation = Session["activitydropdown"];
I can see text and value and selected is false for every item. So how can i carry text here selected from Index to httpost, so when user selects list from dropdown, it stores that text value.
It will be available in your Request i.e.
Request["DrpaActivity"]
However I would strongly advise using ViewModels instead as they're typesafe, less room for error and easier to use.
If you create a view model, like below:
public class AViewModel
{
public string DrpaActivity { get; set; }
public List<SelectListItem> ActivitySelectList { get; set; }
}
In your Index you can return it like this:
public ActionResult Index()
{
var model = new AViewModel();
// set the select list i.e.
model.ActivitySelectList = // get from db etc
return View(model);
}
Then in your view declare the model at the top
#model AViewModel
...
Set your dropdown like this:
#Html.DropDownListFor(m => m.DrpaActivity, Model.ActivitySelectList as List<SelectListItem>, "All", new { style = "margin-left:694px;margin-bottom:20px;", onchange = "submit();" })
You can then get your selected drop-down in your post as follows:
[HttpPost]
public ActionResult Index(AViewModel model)
{
var isValid = model.DrpaActivity;
return View(model);
}
I have a dropdownlistfor:
#Html.DropDownListFor(model => model.Item.Item.Status, new SelectList(#Model.AllStatus, "id", "Description"), new { id = "statusDropdown" })
#Html.ValidationMessageFor(model => model.Item.Item.Status)
HTML output:
<select id="statusDropdown" class="valid" name="Item.Item.Status" data-val-required="The Status field is required." data-val-number="The field Status must be a number." data-val="true">
<option value="2">Completed by Admin</option>
<option value="3">General Error</option>
<option value="4">New</option>
</select>
How can I update this code to set a default selected option? E.G.
<option value="4" selected>New</option>
I tried:
#Html.DropDownListFor(model => model.Item.Item.Status, new SelectList(#Model.AllStatus, "id", "Description",#Model.SelectedStatusIndex), new { id = "statusDropdown" })
#Model.SelectedStatusIndex has a value of 4, but does not change the default option to New.
I also tried:
#Html.DropDownListFor(model => model.SelectedStatusIndex, new SelectList(#Model.AllStatus, "id", "Description"), new { id = "statusDropdown" })
#Html.ValidationMessageFor(model => model.Item.Item.Status)
This selects the default option "New", but model.Item.Item.Status is not set by the dropdown on HTTP POST.
Other Detail:
model.Item.Item.Status is an int. #Model.AllStatus is a SQL table that lists all available status options.
There exist already some discussions about that here or there. One of the problems might be using a different type than string for the key value. I had similar problems in past and I know that i solved it like this - explicitly setting the Selected property when preparing the list (in your case, AlLStatus).
Would mean, for your case (in controller action):
IEnumerable<SelectListItem> selectList =
from s in allStatus // where ever you get this from, database etc.
select new SelectListItem
{
Selected = (s.id == model.Item.Item.Status),
Text = cs.Description,
Value = s.id.ToString()
};
model.AllStatus = selectList;
This is in addition to the answers above. This is how I would have done it.
The view model is there to represent your data. So for a single drop down list I would have the following:
public class MyViewModel
{
public int StatusId { get; set; }
public IEnumerable<Status> Statuses { get; set; }
}
And the Status class would look like this:
public class Status
{
public int Id { get; set; }
public string Description { get; set; }
}
The controller's action method to handle the view:
public class MyController
{
private readonly IStatusService statusService;
public MyController(IStatusService statusService)
{
this.statusService = statusService;
}
public ActionResult MyActionMethod()
{
MyViewModel viewModel = new MyViewModel
{
Statuses = statusService.GetAll(),
StatusId = 4 // Set the default value
};
return View(viewModel);
}
}
The view will look like this:
#model MyProject.ViewModels.MyViewModel
#Html.DropDownListFor(
x => x.StatusId,
new SelectList(Model.Statuses, "Id", "Description", Model.StatusId),
"-- Select --"
)
#Html.ValidationMessageFor(x => x.StatusId)
There you go.
I ended up using a variant of thomasjaworski's answer.
View:
#Html.DropDownListFor(model => model.SelectedStatusIndex, new SelectList(#Model.StatusSelectList, "Value", "Text"), new { id = "statusDropdown" })
ViewModel constructor
StatusSelectList = AllStatus.Select(x =>
new StatusSelectListItem
{
Text = x.Description,
Value = x.id.ToString()
}).ToList();
this.SelectedStatusIndex = 2;//Default Status is New
Controller on HTTP POST
I set model.Item.Item.Status seperately from the dropdown itself:
model.Item.Item.Status = model.SelectedStatusIndex;
because the dropdown set's the value of the expression passed as the first argument:
#Html.DropDownListFor(model => model.SelectedStatusIndex, new SelectList(#Model.StatusSelectList, "Value", "Text"), new { id = "statusDropdown" })
In this case model.SelectedStatusIndex is what is set by the dropdown. This controller implementation is what I found to be tricky.
You can use "Insert" for adding default value of Dropdown and add it to your Dynamic list :
By this way you don't need to use Razor in your View.
List<Y> m = X.GetList();
m.Insert(0, new Y{ Name = "--Select--" });
SelectList ProductSizeList = new SelectList(_context.Sizes, "SizeId", "SizeName");
//after you create the selectList you have to create the default select list item
SelectListItem AllSize = new SelectListItem("All Size", "0");
// and after this you add this item to the begin of the selectlist
ViewData["SizeId"] = ProductSizeList.Prepend(AllSize);
I assign DropDownListFor's expression with value which is already defined in List. It works for me. I use List<SelectListItem> Model.IncidentPriorityList for ddwn's selectlist.
Model.incident.INCIDENT_PRIORITY_ID = Model.DefaultParameterId;
#Html.DropDownListFor(m => m.incident.INCIDENT_PRIORITY_ID, Model.IncidentPriorityList, "Select", new { #class = "form-control selectpicker", id = "drpPriority", #required = true })
I want to select the default value in drop down list where policyId = 7 but it didn't select that value, what i am doing wrong?
Controller:
var pm = new ManagerClass();
IEnumerable<myClass> po = pm.GetDataFromDb();
IEnumerable<SelectListItem> Policies = new SelectList(po, "PolicyID", "PolicyName", new { PolicyID = 7 });
ViewBag.Policies = Policies;
View:
#Html.DropDownListFor(m => m.PolicyID, ViewBag.Policies as IEnumerable<SelectListItem>, new { #class = "dropdown-field"})
It's because it's not actually selecting the value in the SelectList.
First, to make it nicer, put the items in your view model to prevent the cast (this is better practice too):
public class MyModel
{
public int PolicyID { get; set; }
public List<SelectListItem> Policies { get; set; }
//rest of your model
}
Then populate it:
var model = new MyModel();
model.Policies = po
.Select(p => new SelectListItem
{
Text = p.PolicyName,
Value = p.PolicyID.ToString(),
Selected = p.PolicyID == currentPolicyId //change that to whatever current is
})
.ToList();
Then in your view, do:
#Html.DropDownListFor(m => m.PolicyID, Model.Policies, new { #class = "dropdown-field"})
Just set the PolicyID property on your view model to the value you want to be preselected:
var pm = new ManagerClass();
var po = pm.GetDataFromDb();
ViewBag.Policies = new SelectList(po, "PolicyID", "PolicyName");
viewModel.PolicyID = 7;
return View(viewModel);
Since your DropDownList is bound to the PolicyID property (m => m.PolicyID), then its value will be used when deciding which element to be preselected.
In case that you have a static menu:
1- create the following class:
public static class StaticMenus
{
public static List<string> GetGridRowsCount()
{
List<string> result = new List<string>();
result.Add("3");
result.Add("5");
result.Add("10");
result.Add("20");
result.Add("25");
result.Add("50");
result.Add("100");
return result;
}
}
2- add the following code to your controller :
ViewData["CountryList"] = new SelectList(StaticMenus.GetGridRowsCount(),"10");
3- add the following code to your view:
#Html.DropDownList("MainGridRowsCount", ViewData["RowsCountList"] as SelectList)
I'm a bit confused by the behavior of ASP.NET MVC with it not changing the value of a dropdown list after a POST. Can someone explain how to do this.
First of all I have a model that looks like this:
public class Test
{
public int OneID { get; set; }
public IEnumerable<SelectListItem> OneList
{
get
{
yield return new SelectListItem
{
Text = "Red",
Value = "0"
};
yield return new SelectListItem
{
Text = "Green",
Value = "1"
};
yield return new SelectListItem
{
Text = "Blue",
Value = "2"
};
}
}
public int TwoID { get; set; }
public IEnumerable<SelectListItem> TwoList
{
get
{
yield return new SelectListItem
{
Text = "Ruby",
Value = "0"
};
yield return new SelectListItem
{
Text = "Gem",
Value = "1"
};
yield return new SelectListItem
{
Text = "Bronze",
Value = "2"
};
}
}
}
The view has this snippet of code in the body content:
<% using (Html.BeginForm("Index", "Home", FormMethod.Post))
{ %>
<table>
<tr>
<td>
<% =Html.DropDownList("OneID", Model.OneList, new
{ #onchange = "this.form.submit();" })%>
</td>
<td>
<% =Html.DropDownList("TwoID", Model.TwoList)%>
</td>
</tr>
</table>
<% } %>
And the GET and POST actions look like this:
public ActionResult Index()
{
Test test = new Test();
test.OneID = 0;
test.TwoID = 0;
return View(test);
}
[AcceptVerbs(HttpVerbs.Post)]
public ActionResult Index(Test test)
{
test.TwoID = test.OneID;
return View(test);
}
What I'm trying to achieve is to change the selected item in the second drop down to match the first drop down each time the first drop down is changed. So I'm getting the selected value from the first drop down and assigning it to the ID used for the second drop down and then returning the same model. The first drop down is correctly set in the view but not the second one.
Ideas?
The reason this doesn't work the way you expect it is because when the DropDownList helper tries to render the select element it first looks for posted values that match the name which in this case is TwoID and use this value instead of the value in the model. This is the same with a TextBox for example. If you use this helper and in the POST controller action you modify the value of the model it will still show the old value. That's just how helpers work. They bind from POSTed values.
There are two possible workarounds:
Use javascript to synchronize both dropdowns:
#onchange = "document.getElementById('TwoID').value = this.value; this.form.submit();"
BTW this should be done in an unobtrusive way in a separate javascript file:
$(function() {
$('#OneID').change(function() {
$('#TwoID').val($(this).val());
this.form.submit();
});
});
Write your own helper or generate the select manually (less recommended)