2016-07-16 2 views
1
Ich erstelle eine MVC-Zeitplanungs-App und ich habe 3 CodeFirst EF6-Klassen in einer Viele-zu-Viele-Konfiguration mit der mittleren Tabelle, die zusätzliche Informationen wie Uhrzeit, Datum usw. des Treffens zwischen dem Gastgeber und seinen Besuchern. Ich habe ein ViewModel erstellt, mit dem ich Hosts, Besucher und Besprechungen auf einer einzigen Seite erstellen kann, anstatt die einzelnen Ressourcen einzeln für die einzelnen Sitzungen erstellen zu müssen. Der Controller und die Ansicht für diese Anordnung erzeugen einige Fragen.

Nicht-Datenbank-Feld oben in SelectList für Razor-Ansicht in MVC einschließen 5

Ich bin vorbei, mit ViewBag, eine Select der Ansicht

ViewBag.HostID = new SelectList(db.Hosts.OrderBy(x => x.Name), "id", "Name"); 

und

ViewBag.VisitorID = new SelectList(db.Visitors.OrderBy(x => x.LastName). 
ThenBy(y => y.FirstName), "id", "VisitorName"); 

, die erfolgreich in meinem Razor Ansicht

jedoch

<div class="form-group"> 
     @Html.LabelFor(model => model.HostID, "HostID", htmlAttributes: new { @class = "control-label col-md-2" }) 
     <div class="col-md-10"> 
      @Html.DropDownList("HostID", null, htmlAttributes: new { @class = "form-control" }) 
      @Html.ValidationMessageFor(model => model.HostID, "", new { @class = "text-danger" }) 
     </div> 
    </div> 

    <div class="form-group"> 
     @Html.LabelFor(model => model.VisitorID, "VisitorID", htmlAttributes: new { @class = "control-label col-md-2" }) 
     <div class="col-md-10"> 
      @Html.DropDownList("VisitorID", null, htmlAttributes: new { @class = "form-control" }) 
      @Html.ValidationMessageFor(model => model.VisitorID, "", new { @class = "text-danger" }) 
     </div> 
    </div> 
mit gerendert wird, Ich möchte in der DropDownList eine Zeile auswählen können, die keine HostID oder VisitorID suc zugeordnet ist h, dass ich dann einen neuen Host oder Besucher eingeben kann und mein Controller die erforderlichen Datensätze erstellt, wenn das Formular zurückgesendet wird.

Daher meine Frage ist, wie füge ich ein Nicht-Datenbank-Feld an den Anfang der SelectList, die dem Controller (einmal zurückgebucht) bedeutet, dass ein neuer Datensatz anstelle einer Referenz auf einen vorhandenen Host erstellt werden soll verwendet werden?

+0

den 'SelectList' Nach dem Erstellen verwenden' .ToList() 'auf dem resultierenden' IEnumerable 'und' verwendet Insert() 'zu je sein würde, -wird ein neues 'SelectListItem' geben Aber es ist nicht klar, wie Sie es verwenden würden - Sie kennen keine Informationen über den' Host' oder 'Visitor' aus den geposteten Daten, also was würden Sie in die Datenbank einfügen? –

+0

Es gibt zusätzliche Formularelemente in der Razor-Datei, die ausgefüllt werden müssen, wenn ein Besucher, der nicht in der Liste enthalten ist, benötigt wird. –

+0

Dann können Sie es einfach tun, wie im ersten Kommentar (oder 'ViewBag.HostID = neue Liste

Antwort

1

Sie können Ihre SelectList mit

ViewBag.HostID = new List<SelectListItem>() 
{ 
    new SelectListItem() 
    { 
     Value = "-1", // note, do not make this "0" unless you make HostID nullable 
     Text = "New Host" 
    } 
}.Concat(db.Hosts.OrderBy(x => x.Name).Select(x => new SelectListItem() 
{ 
    Value = x.id.ToString(), 
    Text = x.Name 
})); 

Hinweis erstellen, die Sie sollten nicht Ihre ViewBag Eigenschaft den gleichen Namen wie die Eigenschaft auf Ihre verbindlich zu benennen (siehe this answer) und Sie sollten mit einem IEnumerable<SelectListItem> HostList mit Blick Modell sein so dass in der Ansicht binden Sie stark zu Ihrer Ansicht Modell

@Html.DropDownListFor(m => m.HostID, Model.HostList, "-Please select-", new { @class = "form-control" }) 

jedoch ein besserer Ansatz, das Problem zu lösen, eine neue Option zumHinzufügenwürde eine Schaltfläche "Add new host" enthalten, die ein modales Formular zum Erstellen des Host anzeigt und Ajax verwendet, um es zu übermitteln, und bei Erfolg die neue Option an das DOM anhängen. Der Umriss Code wäre

@using (Html.BeginForm()) 
{ 
    .... 
    @Html.DropDownListFor(m => m.HostID, Model.HostList, "-Please select-", new { @class = "form-control" }) 
    <button type="button" id="addhost">Add new Host</button> 
    .... 
} 
<div id="hostmodal"></div> 

$('#addhost').click(function() { 
    $('#hostmodal').load('@Url.Action("Create", "Host")); 
    // reparse the validator 
}); 

wo die Create() Methode der HostController eine Teilansicht einer Form zurückkehrt, um ein neues Host Erstellen (siehe this answer für neuparsen der validator)

dann das .submit() Ereignis des Griff ' Erstellen Sie das Formular des Hosts, brechen Sie es ab und senden Sie die Werte mit ajax an eine Methode, die das neue ID von Host in einer JsonResult() zurückgibt. Mit dem zurückgegebenen Wert ID und Name aus dem Formular können Sie ein neues Element <option> anhängen und auswählen.

$('#hostmodal').on('submit', '#hostform', function() { 
    var data = $(this).serialize(); 
    var url = '@Url.Action("Create", "Host")'; 
    var text = ... // a value from the form that you want as the option text 
    $.post(url, data, function(response) { 
     if (response) { 
      $('#HostID').append($('<option></option>').val(response).text(text)).val(response); 
     } else { 
      // Oops 
     } 
    }).fail(function() { 
     // Oops 
    }); 
    // ... close the modal 
    return false; // cancel the default submit 
}); 

Hinweis: Wenn Sie die neue Host hinzugefügt in Sortierreihenfolge verweisen this answer, haben wollen.

und die POST-Methode so etwas wie

[HttpPost] 
public JsonResult Create(HostViewModel model) 
{ 
    // Initialize a new Host data model and set its properties based on the view model 
    var host = new Host() 
    { 
     Name = model.Name, 
     .... 
    } 
    // Save it 
    db.Hosts.Add(host); 
    db.SaveChanges(); 
    // Return its ID 
    return Json(host.ID); // or return Json(null); if error 
} 
+0

Vielen Dank Ich denke, ich folge all dem. Gib mir etwas Zeit, um es umzusetzen und alle Details zu verstehen, die ich verstehen muss und ich werde kommen zurück –

+0

Ich glaube, ich bin nah dran, aber keine Zigarre Ich kann die Felder anzeigen, wenn ich auf "Neuen Besucher hinzufügen" klicke, aber wenn ich klicke k "Besucher speichern" Die jQuery wird nicht ausgeführt. Ich sehe aus wie das Skript nicht registriert ist. Ich werde in Kürze neue Fragen stellen und einen Link hier posten. –

+0

Verwandte Frage, die hier gestellt wird - http://stackoverflow.com/questions/38418163/using-jquery-and-partial-views-to-add-a-new-dropdownlist-item-in-mvc –

Verwandte Themen