asp.net mvc 3 预选 Html.DropDownListFor 不在书呆子晚餐中工作
了解下拉列表,我尝试为 nerddinner 添加 RSVP 创建页面,如 Scott Gu 的博客,带有 Html.DropDownList 用于列出可用的晚餐。
我可以填充下拉列表,但无法让下拉列表预先选择我想要的值(“示例晚餐 2”)。我使用初始化程序在数据库中播种一些晚餐对象。数据库是 sql ce 4,使用 EF“代码优先方法”。抱歉,我知道这是一个常见问题,并且不想问,但老实说,我在这方面花了相当多的时间,但无法让它工作:
ViewModel
public class RSVPViewModel
{
public SelectList DinnersList { get; set; }
public RSVP Rsvp { get; set; }
public string SelectedItem { get; set; }
}
Controller
//
//GET: /RSVP/Create
public ActionResult Create()
{
RSVP rsvp = new RSVP();
string selected = "Sample Dinner 2";
var typeList = new SelectList(dbc.Dinners.ToList(), "DinnerID", "Title", selected);
var viewModel = new RSVPViewModel { DinnersList = typeList, Rsvp = rsvp, SelectedItem = selected };
return View("Create", viewModel);
}
View< /strong>
@Html.DropDownListFor(model => model.Rsvp.DinnerID, Model.DinnersList)
HTML 结果
<select data-val="true" data-val-number="The field DinnerID must be a number." data-val-required="The DinnerID field is required." id="Rsvp_DinnerID" name="Rsvp.DinnerID">
<option value="1">Sample Dinner 1</option>
<option value="2">Sample Dinner 2</option>
</select>
因此,在页面加载时,不会预先选择值为“示例晚餐 2”的下拉列表。当我做出选择并单击提交时,列表显示正常并设置正确的晚餐 ID。
也尝试一下:
@Html.DropDownListFor(x => x.SelectedItem, Model.DinnersList)
但没有设置或绑定到 Rsvp.DinnerID。
这从列表中预选但不绑定(或设置 Rsvp.DinnerID)
@Html.DropDownList("DinnersList")
我想保留它 mvc3 所以想使用 ViewModel 方法(无 ViewData)并最好使用 Html.DropDownListFor (不是 Html.DropDownList)来实现强类型。Viewbag 似乎对于这种情况是不必要的。
谢谢!
Edit1
认为我应该使用 selectListItems 的 selectList 我尝试了这种详细的方法:
RSVP rsvp = new RSVP();
string selected = "2";
List<SelectListItem> dinners = new List<SelectListItem>();
foreach (Dinner dinner in dbc.Dinners.ToList())
{
SelectListItem slDinner = new SelectListItem();
slDinner.Value = dinner.DinnerID.ToString();
slDinner.Text = dinner.Title;
slDinner.Selected = (slDinner.Value == selected);
dinners.Add(slDinner);
}
var dinnersList = new SelectList(dinners, "Value", "Text", selected);
var viewModel = new RSVPViewModel { DinnersList = dinnersList, Rsvp = rsvp, SelectedItem = selected };
但是仍然没有效果。我应该以某种方式使用 @Html.DropDownListFor.. 中的 ViewModel SelectedItem 属性吗?类似于:
@Html.DropDownListFor(x => x.SelectedItem, Model.DinnersList)
但如何获取选定值来设置 Rsvp.DinnerID。我想这就是所谓的绑定。
Learning about dropdown lists, Im trying to add a RSVP create page for nerddinner as in Scott Gu's blog with a Html.DropDownListFor listing available dinners.
I can get the dropdown list populated but I cannot get the dropdown to pre select the value ("Sample Dinner 2") I want. Im using an initilizer to seed a few dinner objects in the db. The database is sql ce 4 using a EF 'code first approach'. Sorry I know this is a v common problem and hate to ask, but honestly have spent quite some time on this but cant get it to work:
ViewModel
public class RSVPViewModel
{
public SelectList DinnersList { get; set; }
public RSVP Rsvp { get; set; }
public string SelectedItem { get; set; }
}
Controller
//
//GET: /RSVP/Create
public ActionResult Create()
{
RSVP rsvp = new RSVP();
string selected = "Sample Dinner 2";
var typeList = new SelectList(dbc.Dinners.ToList(), "DinnerID", "Title", selected);
var viewModel = new RSVPViewModel { DinnersList = typeList, Rsvp = rsvp, SelectedItem = selected };
return View("Create", viewModel);
}
View
@Html.DropDownListFor(model => model.Rsvp.DinnerID, Model.DinnersList)
HTML Result
<select data-val="true" data-val-number="The field DinnerID must be a number." data-val-required="The DinnerID field is required." id="Rsvp_DinnerID" name="Rsvp.DinnerID">
<option value="1">Sample Dinner 1</option>
<option value="2">Sample Dinner 2</option>
</select>
So is not preselecting the dropdownlist with the value "Sample Dinner 2" when the page loads. The list displays ok and sets the correct DinnerID when I make a selection and click Submit.
Tries this also:
@Html.DropDownListFor(x => x.SelectedItem, Model.DinnersList)
but doesnt set or bind to Rsvp.DinnerID.
This preselects from the list but doesnt bind (or set Rsvp.DinnerID)
@Html.DropDownList("DinnersList")
I want to keep it mvc3 so want to implement with strong type using ViewModel approach (no ViewData) and preferably using Html.DropDownListFor (not Html.DropDownList).Viewbag seems unnecessary for this case.
Thanks!
Edit1
Thinking I should be using a selectList of selectListItems I tried this verbose approach :
RSVP rsvp = new RSVP();
string selected = "2";
List<SelectListItem> dinners = new List<SelectListItem>();
foreach (Dinner dinner in dbc.Dinners.ToList())
{
SelectListItem slDinner = new SelectListItem();
slDinner.Value = dinner.DinnerID.ToString();
slDinner.Text = dinner.Title;
slDinner.Selected = (slDinner.Value == selected);
dinners.Add(slDinner);
}
var dinnersList = new SelectList(dinners, "Value", "Text", selected);
var viewModel = new RSVPViewModel { DinnersList = dinnersList, Rsvp = rsvp, SelectedItem = selected };
However still no work. Should I be making use of the ViewModel SelectedItem property in: @Html.DropDownListFor.. somehow? Something like :
@Html.DropDownListFor(x => x.SelectedItem, Model.DinnersList)
but how to I get a selected value to set Rsvp.DinnerID. I think thats called binding.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(5)
阅读此处和这里,我终于明白了 HtmlDropDownlistFor 如何根据您的模型自动在下拉列表中选择正确的项目 - 选择晚餐 ID在RSVP(晚餐.dinnerID 的外键)中将导致包含晚餐.晚餐ID 列表的下拉列表预先选择该值。我认为 SelectList 或 ViewModel 中的 selectedValue 还不需要。
解决方案:
After reading here and here, I finally understand how HtmlDropDownlistFor automatically selects the correct item in the dropdown based on your model - selecting a dinnerID in RSVP (foreign key to dinner.dinnerID) will cause the dropdown containing list of Dinner.DinnerIDs to pre select that value. No need yet I think for selectedValue in the SelectList or ViewModel.
Solution:
您使用的
SelectList
构造函数是应该提供选定的值,但您正在提供选定的文本。您可能想尝试:The
SelectList
constructor you're using is supposed to provide the selected value, but you are providing the selected text. You may want to try:Html.DropDownList 仅在绑定属性为 int 时才有效。任何其他类型(例如命名枚举)都会导致它默认为第一项。
向您的模型添加一个属性,输入 int,它包含您要维护的枚举:
无需在 SelectList 中使用 Selected - Html.DropDownList 会很好地同步。
Html.DropDownList only works if the bound property is an int. Any other type, such as a named enum, will cause it to default to the first item.
Add a property to your Model, type int, which wraps the enum you are trying to maintain:
No need to use Selected in your SelectList - Html.DropDownList will synchronise just fine.
请注意是否存在具有相同名称的查询字符串,它将覆盖该行为,不确定是否具有相同名称的隐藏字段。
例如
Please take care if there is a QUERY STRING with same name , it will override that behavior, Not sure about HIDDEN FIELDS with same name.
E.g.
Html.DropDownList 接受 int 属性,DropDownListFor 也接受,但你必须小心你在做什么。我检查了 ASP.NET MVC 3 中的 SelectExtensions.cs 并发现了这一点:
When you use DropDownList("XyField", "default") to create a DropDown, then you必须将选择列表放入 ViewBag.XyField 和 DropDownList() 句柄中这是正确的。
当您使用 DropDownListFor(m=>m.XyField, ... ) 时,您可以显式传递选择列表,如下所示:
DropDownListFor(m=>m.XyField, ViewBag.XyFieldList as IEnumerable)
当您执行此操作时,会发生以下情况:
注意:如果您将选择列表存储在 ViewBag.XyField 中,则在访问模型之前就会找到它。 不想将“selectList.ToString()”与“selectList[i”进行比较].Value”来预先选择您的选项。将您的选择列表存储在另一个地方!
有趣的是,您可以将 DropDownListFor 与隐式选择列表一起使用,就像您期望从 DropDownList() 中使用的方式一样。在这种情况下,您甚至可以将列表存储在 ViewBag.XyField 中。要实现此功能,您只需使用 null 作为第二个参数来调用帮助器:
DropDownListFor(m=>m.XyField, null)
然后,从 ViewBag.XyField 中提取选择列表,并跳过上面列表中的步骤 3。因此,如果 XyField 处于模型状态,则这将优先于选择列表中您自己的 Selected 属性,但否则,选择列表将“按原样”使用。
问候
罗尔夫
Html.DropDownList accepts int properties, DropDownListFor too, but you have to be careful what you are doing. I examined the SelectExtensions.cs from ASP.NET MVC 3 and found this:
When you use DropDownList("XyField", "default") to create a DropDown, then you must place the select list into ViewBag.XyField and DropDownList() handles this correctly.
When you use DropDownListFor(m=>m.XyField, ... ), you can pass the select list explictly, like this:
DropDownListFor(m=>m.XyField, ViewBag.XyFieldList as IEnumerable)
When you do this, this following happen:
Attention here: if you stored your select list in ViewBag.XyField, it will be found before the model is accessed. The don't want to compare "selectList.ToString()" with "selectList[i].Value" to preselect your options. Store your selection list in another place!
The funny thing is, you CAN use DropDownListFor with an implicit select list, in the same way as you expect it from DropDownList(). In this case, you will even store your list in ViewBag.XyField. To make this work, you simply have to call the helper with null as second parameter:
DropDownListFor(m=>m.XyField, null)
Then, the select list is pulled from ViewBag.XyField and step 3 in the list above is skipped. So, if XyField is in the model state, this will take precedence before your own Selected properties in the select list, but otherwise, the select list will be used "as is".
Greetings
Rolf