Note that there are some explanatory texts on larger screens.

plurals
  1. POIEnumerable Model and Create Field on the Same Page
    primarykey
    data
    text
    <p>(This post is candy-obfuscated; obfuscated because I have to, candy for the lulz. Trust me, the real thing is actually worthwhile.)</p> <p>Using ASP.NET MVC 4 and EF 5, I'm trying to create a page that simultaneously shows a list of entities that currently exist in the database and a simple create field at the bottom. I have a functioning way of doing it, but I'm wondering if there's a better way, because my current one feels very roundabout. I'd upload an image of what I've got, but I have to have at least ten reputation, so... on to the post.</p> <p>The model I'm passing in looks like so:</p> <pre><code>public class CandyBrand { public int ID { get; set; } [Required(ErrorMessage = "Brand name is required.")] [Display(Name = "Brand Name")] public string Name { get; set; } } </code></pre> <p>The controller looks like this, including both GET and POST methods:</p> <pre><code>public ActionResult CandyBrands() { return View(context.CandyBrands); } [HttpPost] [ValidateAntiForgeryToken] public ActionResult CandyBrands(CandyBrand brand) { if (ModelState.IsValid) { context.CandyBrands.Add(brand); context.SaveChanges(); //try/catch block removed for brevity } return View(db.CandyBrands); } </code></pre> <p>And my view:</p> <pre><code>@model IEnumerable&lt;CandyDatabase.Models.CandyBrands&gt; @{ ViewBag.Title = "Brands"; } &lt;h2&gt;Brands&lt;/h2&gt; &lt;p&gt;@Html.DisplayNameFor(m =&gt; m.Name)&lt;/p&gt; @foreach (var brand in Model) { &lt;p&gt;@Html.DisplayFor(m =&gt; brand.Name)&lt;/p&gt; } &lt;h3&gt;Create New&lt;/h3&gt; @using (Html.BeginForm()) { @Html.AntiForgeryToken() &lt;p&gt;@Html.EditorFor(m =&gt; m.FirstOrDefault().Name) &lt;input type="submit" value="Create" /&gt;&lt;/p&gt; &lt;p&gt;@Html.ValidationMessageFor(m =&gt; m.FirstOrDefault().Name)&lt;/p&gt; } &lt;p&gt;@Html.ActionLink("Back to Candy List", "Index", "Home")&lt;/p&gt; @section Scripts{ @Scripts.Render("~/bundles/jqueryval") @Scripts.Render("/Scripts/clear-inputs.js") } </code></pre> <p>Because I'm passing in a list of candy brands, the model takes on the type IEnumerable. This isn't a problem for the first half - the foreach loop takes care of this. However, this creates other problems further down the page. Because the model is an IEnumerable, Html.EditorFor doesn't like it. Currently, to solve this, I'm calling FirstOrDefault, which brings it down to one entry. This is annoying in and of itself, but it doesn't stop there; MVC then automatically (and unwantedly (which may or may not be a word)) fills the editor with the data from the first entity in the model! If you notice at the bottom, there's a call to a 'clear-inputs' script; this script exists SOLELY to fix this problem by running</p> <pre><code>$("input[type!='submit']").val(""); </code></pre> <p>to clear all the fields when the page loads.</p> <p>Is there a better way to do this? I'm not above accepting the answer "Use a view model, dangit!", but it seems silly to have a view model that has a CandyBrand entity and then a list of CandyBrand entities.</p>
    singulars
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload