2012-07-14 10 views
11

के लिए Asp.Net MVC 3 संपादक हम एक गतिशील संपत्ति के साथ काम करने के लिए संपादक-टेम्पलेट प्राप्त करने का प्रयास कर रहे हैं - इसका कोई फायदा नहीं हुआ। शायद आप में से एक हमारी मदद कर सकता है।गतिशील संपत्ति

public class Criterion 
{ 
    ... 
    public string Text { get; set; } 
    public dynamic Value { get; set; } 
    public Type Type { get; set; } 
    ... 
} 

हमारे उस्तरा दृश्य एक मॉडल है जो प्रत्येक उस में मापदंड की एक सूची है अनुभागों की एक सूची containg हो जाता है:

यहाँ मोटे तौर पर हमारे वर्ग है। (अंश)

@for (int i = 0; i < model.Sections.Count(); i++) 
{ 
    for (int j = 0; j < model.Sections[i].Criteria.Count(); j++) 
    { 
     var criterion = model.Sections[i].Criteria[j]; 
     var type = criterion.Type.Name; 
     var name = "Sections[" + i + "].Criteria[" + j + "].Value"; 
     var criterionDisplayName = criterion.Text; 
     <label for="[email protected](i)[email protected](j)__Value">@criterionDisplayName</label> 
     @Html.Editor(name, type) 
    } 
} 

यह उदाहरण के लिए प्रदर्शन एक चेकबॉक्स सही ढंग से, लेकिन यह मूल्य का उपयोग नहीं करता है: अपने वास्तविक प्रकार के बारे में - (हम कार्यावधि में इन infos मिल।) इन सभी मानदंडों को संपादन मोड में प्रदर्शित किया जाना चाहिए चेकबॉक्स स्थिति को सही ढंग से सेट करने के लिए (मानदंड की जांच की गई है। वैल्यू सत्य है)। अन्य प्रकार के लिए जाता है, जैसे ints। (यह POST अनुरोध के बाद फ़ॉर्म को सही तरीके से भरता है, लेकिन ऐसा इसलिए है क्योंकि एमवीसी उपयोगकर्ता इनपुट को पुन: बनाने के लिए एक अस्थायी मॉडल का उपयोग करता है।)

जितना हमने कोशिश की है और शोध किया है: क्या संपादक का उपयोग करना भी संभव है प्रकार dynamic के गुणों के साथ टेम्पलेट? यदि हां - हम इसे कैसे काम कर सकते हैं? (हम संभावित प्रकार के अनुसार समझना नहीं चाहते हैं। हम वास्तविक प्रकार के आधार पर सही संपादक टेम्पलेट का उपयोग करने के लिए एमवीसी फ्रेमवर्क चाहते हैं।)

उत्तर

15

डायनेमिक्स बिल को अच्छी तरह से एएसपी.NET के साथ फिट नहीं करते हैं MVC। वे मुझे ViewBag के बारे में याद दिलाते हैं और मुझे अपने शरीर के बहुत गहरे कपड़े से ViewBag से नफरत है। तो मैं एक अलग दृष्टिकोण लेगा।

के उदाहरण के लिए निम्नलिखित मॉडल लेते हैं:

public class Criterion 
{ 
    public string Text { get; set; } 
    public object Value { get; set; } 
} 

मूल्य किसी भी प्रकार है कि आप को संभालने के लिए इच्छा हो सकती है। प्रत्येक प्रकार है कि आप को संभालने के लिए आप एक इसी संपादक निर्धारित कर सकते हैं चाहते हैं के लिए अब

@model IList<Criterion> 

@using (Html.BeginForm()) 
{ 
    for (int i = 0; i < Model.Count; i++) 
    { 
     <div> 
      @Html.LabelFor(x => x[i], Model[i].Text) 
      @Html.EditorFor(x => x[i].Value, "Criterion_" + Model[i].Value.GetType().Name) 
     </div> 
    } 

    <button type="submit">OK</button> 
} 

:

public class HomeController : Controller 
{ 
    public ActionResult Index() 
    { 
     var model = new[] 
     { 
      new Criterion { Text = "some integer", Value = 2 }, 
      new Criterion { Text = "some boolean", Value = true }, 
      new Criterion { Text = "some string", Value = "foo" }, 
     }; 
     return View(model); 
    } 
} 

और फिर एक इसी दृश्य:

अब आप एक नियंत्रक जो इस मॉडल भरता हो सकता था टेम्पलेट:

~/Views/Shared/EditorTemplates/Criterion_String.cshtml:

@model string 
@Html.TextBoxFor(x => x) 

~/Views/Shared/EditorTemplates/Criterion_Boolean.cshtml:

@model bool 
@Html.CheckBoxFor(x => x) 

~/Views/Shared/EditorTemplates/Criterion_Int32.cshtml:

@model int 
@{ 
    var items = Enumerable 
     .Range(1, 5) 
     .Select(x => new SelectListItem 
     { 
      Value = x.ToString(), 
      Text = "item " + x 
     }); 
} 

@Html.DropDownListFor(x => x, new SelectList(items, "Value", "Text", Model)) 

जाहिर है ध्यान में रखते हुए इस मॉडल को प्रदर्शित केवल पहला कदम है। मुझे लगता है कि आप उन मानों को प्राप्त करना चाहते हैं जिन्हें उपयोगकर्ता ने कुछ प्रोसेसिंग के लिए पोस्ट नियंत्रक कार्रवाई में वापस दर्ज किया था। इस मामले में कुछ छोटे अनुकूलन आवश्यक हैं। हमें एक कस्टम मॉडल बाइंडर जोड़ने की आवश्यकता है जो रनटाइम पर सही प्रकार को तुरंत चालू करने में सक्षम होगा और कंक्रीट प्रकार को प्रत्येक पंक्ति के लिए छिपे हुए फ़ील्ड के रूप में शामिल करेगा। मैंने पहले से ही this post में एक उदाहरण दिखाया है। इस उदाहरण में भी ध्यान दें कि मैंने सीधे object प्रकार के साथ काम करने के बजाय बेस क्लास का उपयोग किया था।

+0

यह दृढ़ता से टाइप किए गए दृश्य के साथ काम करता है।मैंने दृढ़ता से टाइप किए गए दृश्य का उपयोग न करने के लिए इंडेक्स-व्यू को बदलने का प्रयास किया: हटाया गया '@model IList ' और '@ {var model = (IList ) मॉडल का उपयोग किया गया; } '। फिर मैं '@ Html.Editor (" मॉडल ["+ i +"]। वैल्यू "," मानदंड_ "+ मॉडल [i] .Value.GetType() नाम) ', लेकिन यह मुझे एक त्रुटि देता है - _ मॉडल शब्दकोश में पास किया गया आइटम शून्य है, लेकिन इस शब्दकोश के लिए 'System.Int32' प्रकार के एक गैर-शून्य मॉडल आइटम की आवश्यकता है ._ मैं गलत क्या कर रहा हूं? डिबगिंग मुझे बताता है कि GetType()। इंडेक्स-व्यू में नाम 'Int32' है। – toni

+0

वैसे - हमें दृढ़ता से टाइप किए गए दृश्य का उपयोग करने की आवश्यकता नहीं है, क्योंकि हम किसी तृतीय पक्ष ढांचे (ऑर्चर्ड से सामग्रीशिप) का उपयोग कर रहे हैं। – toni

+0

हम 'ऑब्जेक्ट' के साथ ऊपर के रूप में डार्न्स दृष्टिकोण का उपयोग कर समाप्त हो गए। हमें केवल गतिशील व्यूमोडेल डालना पड़ा और इसे दृढ़ता से टाइप किए गए संपादक टेम्पलेट में पास करना पड़ा। मूल्यवान इनपुट के लिए धन्यवाद, डारिन। – toni

संबंधित मुद्दे