Razor view dropdown list for a model class in MVC3 - asp.net-mvc-3

I have two model class in MVC3 one for Services which have those properties
public int ID { get; set; }
public string Name { get; set; }
public string Description { get; set; }
public string Image { get; set; }
public int ChildOf { get; set; }
It also have a DB table by Entityframework
Another model is Quata which have those properties
public int ID { get; set; }
public string Sender_Name { get; set; }
public string Description { get; set; }
.....
......
public Services Service_ID { get; set; }
It also have a DB table by Entityframework
I want to create a Razor(C#) view (for Quata) where user can send a quata by fill a html form but where i wanna show a dropdown list with Services ID as dropdown value and Services Name as dropdown text which is also come dynamically from the Services DB table .
My question is how i should create that dynamic dropdown list by #Html.DropDownListFor ? and send the selected data from that dropdown list to a Controller ?

Try this
Controller:
public ActionResult Create()
{
var Services = new Services();
Services.Load(); //load services..
ViewBag.ID = new SelectList(Services.ToList(), "Id", "Name");
return View();
}
[HttpPost]
public ActionResult Create(Quata Quata)
{
//save the data
}
A strong Typed View: (Using Razor)
#model Quata
#using (Html.BeginForm()) {
<fieldset>
<legend>Quata</legend>
<div>
#Html.LabelFor(model => model.Service_ID.ID, "Service")
</div>
<div>
#Html.DropDownList("ID", String.Empty)
</div>
<p>
<input type="submit" value="Create" />
</p>
</fieldset>
}

take a look at #Html.DropDownListFor

So say your viewmodel has a list of said Services.
Something that may work for you is the following (you may not need a for loop here, editor is supposed to eliminate that, but I had some weird binding issues).
In your top level view which points at your viewmodel (#model Quata, assuming Quata is your viewmodel) have this code :
#For i = 0 To Model.DropdownListInput.Count - 1
Dim iterator = i
#Html.EditorFor(Function(x) x.DropdownListInput(iterator), "EnumInput")
Next
In your Editor Template (create a subfolder under the view folder this dropdownlist will be in called editor templates and name the template whatever you desire, mine was EnumInput).
In your editor template, which should point at your model for Services (#model Services) have something like the following code (with substitutions for your appropriate variable names):
#<div class="editor-label">
#Html.LabelFor(Function(v) v.value, Model.DisplayName)
</div>
#<div class="editor-field">
#Html.DropDownListFor(Function(v) v.value, New SelectList(Model.ParamEnums, "ValueForScript", "EnumValue"), "--Please Select A Value--")
#Html.ValidationMessageFor(Function(v) v.value)
</div>
Replace the list with your list and the lambda values with yours (#Html.DropDownListFor(x => x.id, New SelectList(x.ServiceList, "ID", "Name"), "--Please Select A Value--") or something like that.
Note that this code is in VB, but it should provide a rough guide.

Related

Inconvenient render partial view MVC 3

I have a partial view of work with a viewmodel, but I have a inconvenience when rendering a partial view in the main view
I get the following message:
The model item passed into the dictionary is of type ‘RolMVC3.Models.USER’ but this dictionary requires a model item of type ‘RolMVC3.Areas. Distributor.Models. LocationViewModel ‘
View Model(LocationViewModel), the ViewModel is within an Area
namespace RolMVC3.Areas.Distributor.Models
{
public class LocationViewModel
{
[Required]
public decimal IdDepartment { get; set; }
[Required]
public string NameCity { get; set; }
[Required]
public string NameNeighborhood { get; set; }
}
}
}
Partial View(_LocationEdit):
#model RolMVC3.Areas.Distributor.Models.LocationViewModel
.....
.....
<div class="editor-label">
#Html.LabelFor(model => model.IdDepartment)
</div>
<div class="editor-field">
#Html.DropDownListFor(model => model.IdDepartment, new SelectList(ViewBag.Department as System.Collections.IEnumerable, "IdDepartment", "NameDepartment", ViewBag.selectedDepartment), "--- Select ---", new { id = "Department"})
#Html.ValidationMessageFor(model => model.Idepartment)
</div>
.....
.....
Main View(Edit):
#model RolMVC3.Models.USER
#{
ViewBag.Title = "Edit User";
}
....
....
#{Html.RenderPartial("_LocationEdit");}
....
....
How I can resolve this?
Blessings
In your Main View(Edit) pass the LocationViewModel , because partial view requires this model and you are not passing it in #Html.RenderPartial
#model RolMVC3.Models.USER
#{
ViewBag.Title = "Edit User";
}
....
....
#{Html.RenderPartial("_LocationEdit",YourLocationViewMODEL);}
....
....
When you call your RenderPartial you need to pass in a model type of LocationViewModel. It doesn't look like you have this in your edit view right now, so you need to either a) add it to the viewbag from your controller and pass it via your RenderPartial call or b) change the model type in your edit view (you may need a wrapper that holds both the user and locationviewmodel information)
[Edit]
The source code would looks something like the following:
// ViewModel
namespace RolMVC3.Areas.Distributor.Models
{
public class EditPageViewModel
{
public LocationViewModel LocationViewModel {get;set;]
public USER User { get; set; }
}
}
// Edit View
#model RolMVC3.Areas.Distributor.Models.EditPageViewModel
#{
ViewBag.Title = "Edit User";
}
....
....
#Html.RenderPartial("_LocationEdit",Model.LocationViewModel);
....
....

Editor Template Not working in MVC3

I am trying out the Editor Template in MVC 3
My model class is
public class BookViewModel
{
public int Id { get; set; }
public string Name { get; set; }
[DataType(DataType.Text)]
public string Author { get; set; }
}
I have create a partial view for Editor template and put that in a EditorTemplates folder with name Text.cshtml. following is the partial view
#inherits System.Web.Mvc.WebViewPage<string>
<p> Write the name of author</p> #Html.TextBox(Model)
and I used #Html.EditorFor in the view page
<p> Name : #Html.EditorFor(model => model.Name)</p>
<p> Author</p> #Html.EditorFor(model => model.Author)
But when I run the program what I see is only an empty TextBox. I should see a TextBox filled with Author Name right?
What am I missing here?
Your editor template should be:
#model String
<p> Write the name of author</p> #Html.TextBox("name of the textbox", Model)
The first parameter of the #Html.TextBox() helper can be an empty string as well, but its not recommended

UIHint does not work with IList?

I have a property in my ViewMode:
[UIHint("FileUpload")]
public IList<string> Images { get; set; }
In view Create.cshtml
#html.ValidationSummary(true)
#html.EditorForModel()
In the folder Shared/EditorTemplates/FileUpload.cshtml
<h3>Test</h3>
But the field is not displayed. Simply, nothing happens!
I did the same test with another type of field and it worked:
[UIHint("FileUpload")]
public string Test { get; set; }
What could be wrong?
How do you solve this problem?
If I manually add the code below in my Create.cshtml view, it works!
#Html.EditorFor(m => m.Images)
I do not know what to do.
Yes, UIHint doesn't work with lists. You will need a loop inside the corresponding editor template (~/Views/Shared/EditorTemplates/FileUpload.cshtml). The UIHint template is passed the model which in this case is a IList<string>.
#model IList<string>
#foreach (var item in Model)
{
...
}

How do I use editortemplates in MVC3 for complex types?

I have two classes, Vat and Product. Product has a property of IVat. I am trying to use editor templates in MVC to display a dropdown list of all the Vat objects when creating/editing a Product. For the dear life of me I cannot get this working.
I have the following code which displays the dropdown but it does not set the Vat for the Product when the form gets submitted.
Controller:
IList<IVatRate> vatRates = SqlDataRepository.VatRates.Data.GetAllResults();
ViewBag.VatRates = new SelectList(vatRates, "Id", "Description");
Add.cshtml
#Html.EditorFor(model => model.VatRate.Id, "VatSelector", (SelectList)ViewBag.VatRates)
VatSelector.cshtml
#model SelectList
#Html.DropDownList(
String.Empty /* */,
(SelectList)ViewBag.Suppliers,
Model
)
I would be grateful if anyone can shed some light on this or even point me to a good example on the web somewhere...I have been stuck with this for quite a few days now.
I would use strongly typed views and view models as it makes things so much easier rather than ViewBag.
So start with a view model:
public class VatRateViewModel
{
public string SelectedVatRateId { get; set; }
public IEnumerable<IVatRate> Rates { get; set; }
}
then a controller:
public class HomeController: Controller
{
public ActionResult Index()
{
var model = new VatRateViewModel
{
Rates = SqlDataRepository.VatRates.Data.GetAllResults()
};
return View(model);
}
[HttpPost]
public ActionResult Index(VatRateViewModel model)
{
// model.SelectedVatRateId will contain the selected vat rate id
...
}
}
View:
#model VatRateViewModel
#using (Html.BeginForm())
{
#Html.DropDownListFor(
x => x.SelectedVatRateId,
new SelectList(Model.Rates, "Id", "Description")
)
<input type="submit" value="OK" />
}
And if you wanted to use editor template for the VatRateViewModel you could define one in ~/Views/Shared/EditorTemplates/VatRateViewModel.cshtml:
#model VatRateViewModel
#Html.DropDownListFor(
x => x.SelectedVatRateId,
new SelectList(Model.Rates, "Id", "Description")
)
and then whenever somewhere you have a property of type VatRateViewModel you could simply:
#Html.EditorFor(x => x.SomePropertyOfTypeVatRateViewModel)
which would render the corresponding editor template.

ModelBinding a List of ViewModels with the MvcContrib Grid

I'm trying to bind a list of model objects to a grid using the MvcContrib Grid helper. Obviously, emitting an HTML table is easy enough, but I'm struggling with returning all the selected rows (or all rows and filtering via a Where(x => x.Selected)).
Here's a dummy version of what I mean:
Model:
public class Player
{
[ScaffoldColumn(false)]
public int Id { get; set; }
public string Name { get; set; }
public int JerseyNumber { get; set; }
public string Position { get; set; }
[ScaffoldColumn(false)]
public bool Selected { get; set; }
}
View:
#model democode.Models.Player
#using (Html.BeginForm())
{
#{
var grid = Html.Grid(Model)
.AutoGenerateColumns()
.Columns(c => c.For(p => Html.CheckBoxFor(_ => p.Selected)).InsertAt(0))
.Columns(c => c.For(p => Html.HiddenFor(_ => p.Id)))
grid.Render();
}
<p>
<input type="submit" value="Submit" />
</p>
}
So, what you are looking at is a grid of hockey players with a checkbox before each one, allowing the user to select one or more. On clicking submit, I'd like for it to post the collection back (understanding that all but Selected and Id would be null/default), but I understand the problem is that the records coming across in the POST data have overlapping keys in the list of key-value pairs.
I have successfully worked around this in the past by hand-writing the HTML table and using the strategy Phil Haack outlines here: http://haacked.com/archive/2008/10/23/model-binding-to-a-list.aspx
My question is, can I do the same thing using the Grid helper from MvcContrib, or is it more work than what it's worth?

Resources