Okay, ich bin mir bewusst, dass dies keine direkte Antwort auf Ihre Frage ist, aber dies ist möglicherweise eine bessere Möglichkeit, die meisten Eingaben zu machen (und es hat Spaß gemacht, sie zu machen). Ich habe dies gerade erst abgeschlossen und einige Tests durchgeführt, daher kann ich nicht dafür bürgen, dass dies in jeder Situation perfekt ist.
Ich habe diese Idee von Jimmy Bogards Post hier bekommen . Schauen Sie mal rein, denn dort gibt es eine Menge wirklich cooler Ideen.
Was ich getan habe, ist ein "InputFor" -Helfer, der sein Bestes versucht, um herauszufinden, welche Eingabe Sie verlangen, und sie entsprechend ausgibt. Dies führt zu Optionsfeldern, standardmäßig jedoch zu einem Dropdown-Menü, wenn mehr als zwei vorhanden sind. Sie sollten diese Funktionalität problemlos ändern können.
Mit dem folgenden Code können Sie Anrufe wie <%= Html.InputFor(m => m.Gender) %>
oder tätigen <%Html.InputFor(m => m.Gender, Model.GenderList)%>
. Am Ende gibt es ein cooles kleines bisschen, mit dem Sie konventionell codieren können, aber wir werden später darauf zurückkommen.
public static MvcHtmlString InputFor<TModel>(this HtmlHelper<TModel> helper, Expression<Func<TModel, object>> field, Dictionary<string, string> listing) where TModel : class
{
string property_name = GetInputName(field);
PropertyDescriptor descriptor = TypeDescriptor.GetProperties(helper.ViewData.Model).Find(property_name, true);
string property_type = descriptor.PropertyType.Name;
var func = field.Compile();
var value = func(helper.ViewData.Model);
if (descriptor.Attributes.Contains(new HiddenInputAttribute()))
{
return helper.Hidden(property_name, value);
}
if (property_type == "DateTime" || property_type == "Date")
{
return helper.TextBox(property_name, value, new { @class = "date_picker" });
}
if (listing != null)
{
if (listing.Count <= 2)
{
string output = "";
foreach (KeyValuePair<string, string> pair in listing)
{
TagBuilder label = new TagBuilder("label");
label.MergeAttribute("for", property_name);
label.SetInnerText(pair.Value);
output += helper.RadioButton(property_name, pair.Key, (value == pair.Key)).ToHtmlString();
output += label.ToString();
}
return MvcHtmlString.Create(output);
}
else
{
return helper.DropDownList(property_name, new SelectList(listing, "Key", "Value"), value);
}
}
else
{
if (property_type == "Boolean")
{
listing = new Dictionary<string, string>();
listing.Add("true", "Yes");
listing.Add("false", "No");
SelectList select_values = new SelectList(listing, "Key", "Value", ((bool)value ? "Yes" : "No"));
return helper.DropDownList(property_name, select_values);
}
return helper.TextBox(property_name, value);
}
}
Kodierung durch Konvention
Der folgende Code ermöglicht dies unter Berücksichtigung der Konvention über die Konfiguration. Ein Beispiel hierfür ist, wenn Sie ein Modellobjekt haben, das die Eigenschaft enthält, die Sie auflisten möchten (Geschlecht), und ein Wörterbuch mit demselben Namen, dem jedoch "Liste" (GenderList) angehängt ist, diese Liste standardmäßig verwendet.
zB <%= Html.InputFor(m => m.Gender) %>
kann eine vollständige Dropdown-Liste / Optionsfeldgruppe erstellt werden, aber diese Standardwerte können durch einen Anruf wie überschrieben werden<%= Html.InputFor(m => m.Gender, alternate_list) %>
public static MvcHtmlString InputFor<TModel>(this HtmlHelper<TModel> helper, Expression<Func<TModel, object>> field) where TModel : class
{
string property_name = GetInputName(field) + "List";
PropertyDescriptor list_descriptor = TypeDescriptor.GetProperties(helper.ViewData.Model).Find(property_name, true);
Dictionary<string, string> listing = null;
if (list_descriptor != null)
{
PropertyInfo temp = helper.ViewData.Model.GetType().GetProperty(property_name);
listing = (Dictionary<string, string>)temp.GetValue(helper.ViewData.Model, null);
}
return InputFor(helper, field, listing);
}
Nun ein kleiner Haftungsausschluss:
- Dies ist nicht der schnellste Code der Welt (aufgrund der Reflexion und anderer Dinge). In meiner Situation ist dies nicht wirklich relevant, da alles benutzergesteuert ist, wenn Sie vorhaben, etwas Verrücktes zu tun.
- Dieser Code steckt noch in den Kinderschuhen. Ich werde ihn in den nächsten Tagen eingehender testen und ergänzen, offen für Vorschläge zur Verbesserung des Codes.
Ich hoffe, dieser Code ist für jemanden nützlich. Ich weiß, dass ich ihn in den nächsten Wochen verwenden werde, um die Zeit zu verkürzen. Dies zu reduzieren, um nur das Optionsfeld zu aktivieren, sollte eine triviale Aufgabe sein, viel Glück :)
Jay