Wits заканчиваются на IDictionary <T, T> и ModelBinders, ASP.NET MVC 2.0 - PullRequest
2 голосов
/ 21 октября 2010

Хорошо, я не пытаюсь сделать что-то сверхсложное, я искал и искал, и бродил по всем блогам и форумам, которые я могу найти.Я собираюсь вырвать мои волосы, потому что никто просто не откроет , покажет , как это работает.

Я хочу использовать IDictionary в моей модели.Не берите в голову причину, это не имеет значения.Я просто хочу сделать что-то очень простое и понять, что происходит.

Может кто-нибудь помочь мне разобраться в HTML, который я должен добавить в представление, чтобы сделать эту работу правильной?Пожалуйста?Я пробовал Html.TextBoxFor, и он возвращает нулевое значение при обратной передаче.Я попытался вручную, используя индекс элемента словаря, и он возвращается нулевым.Я действительно расстраиваюсь, и все, что я вижу, это перенаправление на блоги, которые не отвечают на вопрос.

Контроллер

    public ActionResult DictionaryView()
    {
        var model = new Dictionary<string, int>
        {
            { "First", 0 },
            { "Second", 0 },
            { "Third", 0 },
            { "Fourth", 0 }
        };

        return View(model);
    }

    [HttpPost]
    public ActionResult DictionaryView(Dictionary<string, int> dictionary)
    {
        return null;
    }

HTML

<%@ Page Title="" Language="C#" MasterPageFile="~/Views/Shared/Site.Master" Inherits="System.Web.Mvc.ViewPage<System.Collections.Generic.IDictionary<string,int>>" %>

<asp:Content ContentPlaceHolderID="MainContent" runat="server">

    <h2>Dictionary</h2>
<% using (Html.BeginForm()) {%>
        <%: Html.ValidationSummary(true) %>
    <% for (int i = 0; i < Model.Count; i++) { %>
        **// This is there I am stuck!** 
    <% } %>
            <p>
                <input type="submit" value="Submit" />
            </p>
    <% } %>
</asp:Content>

Ответы [ 4 ]

3 голосов
/ 21 октября 2010

http://www.hanselman.com/blog/ASPNETWireFormatForModelBindingToArraysListsCollectionsDictionaries.aspx

Пример

<%
    int i = 0;
    foreach (KeyValuePair<string, int> pair in Model)
    { %>
    <p>Key: <%= Html.TextBox(String.Format("[{0}].key", i), pair.Key)%></p>
    <p>Value: <%= Html.TextBox(String.Format("[{0}].value", i), pair.Value)%></p>
<%
    i++;
    }
%>

Редактировать: это должно работать

1 голос
/ 21 октября 2010

Вам не хватает понятия, как создать отдельный счетчик, чтобы у вас был индекс, а также перебирать словарь с циклом foreach:

<% using (Html.BeginForm()) {%>
        <%: Html.ValidationSummary(true) %>
        <% int counter = 0;
           foreach (var kv in Model) { %>
            <input type="text" name="dictionary[<%= counter %>].Key" value="<%= kv.Key %>" />
            <input type="text" name="dictionary[<%= counter %>].Value" value="<%= kv.Value %>" />
        <%
           counter++;
           } %>
        <p>
            <input type="submit" value="Submit" />
        </p>
<% } %>

Только что проверил это сейчас, мой Контроллер - ваша КПК.

И, к вашему сведению, я просто прочитал этот пост в блоге, чтобы попасть сюда. Вы просто должны были сопоставить свои элементы HTML с тем, что написал Скотт.

1 голос
/ 21 октября 2010

Stacey,

Я не верю, что ModelBinder (в любом случае по умолчанию) сможет выяснить, что вы пытаетесь сделать, поэтому параметр IDictionary является нулевым.

Ваши вещи будут там в коллекции Request.Params. Например:

Request.Params["First"]

вернет все, что вы ввели в первое текстовое поле. Оттуда вы можете вытащить их вручную.

Если вы хотите, чтобы это работало без использования ViewModel, как предложено @rockinthesixstring, вам, скорее всего, придется написать собственный ModelBinder, который будет делать то, что вы хотите.

Если вам нужен пример этого, дайте мне знать, и я откопаю материал для связывания пользовательских моделей.

Кстати, рабочий вид может выглядеть так:

foreach (var pair in Model)
{
    Response.Write(Html.TextBox(pair.Key, pair.Value));
} 
1 голос
/ 21 октября 2010

Можете ли вы использовать ViewModel (POCO) вместо словаря? Таким образом, ваша модель будет иметь то, что вы можете выбрать.

EDIT


ки. Так что мои отбивные не идеальны без интеллигенции ... извините. Но это моя общая идея

Public Function DictionaryView() As ActionResult

    Dim model = New System.Collections.Generic.List(Of MyDictionary)
    model.Add(new MyDictionary("First", 0))
    model.Add(new MyDictionary("Second", 0))
    model.Add(new MyDictionary("Third", 0))
    model.Add(new MyDictionary("Forth", 0))

    Return View(model)
End Function


''# This would be your view model.
Public Class MyDictionary
    Public Property TheString
    Public Property TheInt
End Class

Тогда, по вашему мнению, вы можете использовать

model.TheString  
model.TheInt
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...