Reputation: 2280
I am trying to use MVC6 Tag Helpers to create a dropdownlist of CountryCode and CountryName so that a user can select their country after registering. The relevant part of the view looks like this so far
<form asp-controller="Manage" asp-action="EditCountry" asp-route-returnurl="@ViewData["ReturnUrl"]">
<div asp-validation-summary="ValidationSummary.ModelOnly" class="text-danger"></div>
<select asp-for="CountryCode" asp-items="@Model.Countries"></select>
The relevant part of the viewmodel looks like this
[Display(Name = "Country")]
public string CountryCode { get; set; }
public IEnumerable<Country> Countries { get; set; }
A Country looks like this
public partial class Country
{
[Key]
public string CountryCode { get; set; }
public string CountryName { get; set; }
public virtual ICollection<ApplicationUser> Users { get; set; }
}
The controller returns a list of countries to the viewmodel
var model = new IndexViewModel
{
CountryCode = user.CountryCode,
Countries =_customersContext.Countries.OrderBy(c=>c.CountryName),
};
return View(model);
but in the view asp-items="@Model.Countries"
has a squiggly Cannot convert Country to SelectListItem
Also I cannot find how in the form to specify CountryCode as the property to return and CountryName as the property to display.
Upvotes: 13
Views: 30298
Reputation: 961
I have proposed an alternative way of doing this by extending the SelectTagHelper
with some more attributes that can make this type of development more convenient. The issue is discussed here.
It is based on a class SelectListDescriptor
that contain the list of items, the property to display the text and value field respectively. Then in the view one simple type
<select asp-descriptor="@ViewBag.CountryDescriptor"><option value="">-- Choose country</option<</select>
.
The country descriptor is just new SelectListDescriptor(nameof(Country.CountryCode), nameof(Country.CountryName), countries)
. This avoid magic strings by utilizing the power of the `nameof-operator
Upvotes: 1
Reputation: 17
public class MyViewModel //MODEL LAYER
{
public int CountryId { get; set; }
public string CountryName { get; set; }
public List<Employee> EmployeesList { get; set; }
}
public class Employee
{
public int Id { get; set; }
public string FullName { get; set; }
}
public IActionResult Contact1() //CONTROLLER
{
MyViewModel N1 = new MyViewModel();
List<Employee> N2 = new List<Employee>()
{
new Employee { Id=1,FullName="sivaragu" },
new Employee { Id=2,FullName="siva" },
new Employee { Id=3,FullName="SENTHIL" }
};
ViewBag.MovieType = N2;
return View();
}
CSHTML(MVC6)
<select asp-for="CountryId" asp-items="@(new SelectList(@ViewBag.MovieType,"Id","FullName") )">
</select>
Upvotes: 2
Reputation: 6011
The way I make my dropdowns is somewhat similar except that in my ViewModel, my property is of type SelectList
instead of an IEnumerable<>
.
public class HomeViewModel
{
public string CountryCode { get; set; }
public SelectList CountryList { get; set; }
}
Then in the controller I get the data and convert it to an anonymous list with two properties “Id” and “Value”.
In turn, I create a new SelectList()
passing in the anonymous list specifying what is the dataValueField
and what is the dataTextField
.
public IActionResult Index()
{
var countries = _customersContext.Countries.OrderBy(c => c.CountryName).Select(x => new { Id = x.Code, Value = x.Name });
var model = new HomeViewModel();
model.CountryList = new SelectList(countries, "Id", "Value");
return View(model);
}
Finally, in the View:
<div class="form-group">
<label asp-for="CountryCode" class="col-md-2 control-label"></label>
<div class="col-md-10">
<select asp-for="CountryCode" asp-items="@Model.CountryList"></select>
</div>
</div>
Upvotes: 47