2010-05-14 7 views
1

В шаблоне MVC2 я обычно использую this.ViewData.TemplateInfo.GetFullHtmlFieldId(fieldName) , чтобы сгенерировать поле id элемента html. Это работает в большинстве случаев.ASP.NET GetFullHtmlFieldId не возвращает действительный id

Однако этот метод не возвращать valid id field, это просто префикс fieldName с ViewData.TemplateInfo.HtmlFieldPrefix, это вызывает проблемы для меня при рендеринге коллекции, имеет [] в HtmlFieldPrefix.

Я вручную преобразовал эти символы в _, где я нахожу необходимость, но это кажется не изящным (повторный код), кто-нибудь нашел хороший способ правильно создать поле идентификатора?

ответ

3

Можете ли вы уточнить, какие проблемы у вас есть?

Например, есть элегантный подход к editing variable length list с validation support. Хотя он не использует шаблоны, все еще остается СУХОЙ с частичными видами.

В то время как идентификаторы несовместимы - имена в порядке и только проблема, с которой я столкнулся, заключается в том, что с использованием jquery.infieldlabel оказалось, что атрибут label для атрибута (сгенерированного GetFullHtmlFieldId внутри помощника LabelFor) не соответствует идентификатору соответствующего ввода TextBoxFor. Таким образом, я создал метод помощника LabelForCollectionItem, который просто использует тот же метод для генерации id, что и TextBox. TagBuilder.GenerateId(fullName)

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

public static class LabelExtensions 
{ 
    /// <summary> 
    /// Generates Label with "for" attribute corresponding to the id rendered by input (e.g. TextBoxFor), 
    /// for the case when input is a collection item (full name contains []). 
    /// GetFullHtmlFieldId works incorrect inside Html.BeginCollectionItem due to brackets presense. 
    /// This method copies TextBox's id generation. 
    /// </summary> 
    public static MvcHtmlString LabelForCollectionItem<TModel, TValue>(this HtmlHelper<TModel> html, Expression<Func<TModel, TValue>> expression, 
       string labelText = null, object htmlAttributes = null) where TModel : class 
    { 
     var tag = new TagBuilder("label"); 
     tag.MergeAttributes(new RouteValueDictionary(htmlAttributes)); // to convert an object into an IDictionary 

     // set inner text 
     string htmlFieldName = ExpressionHelper.GetExpressionText(expression); 
     string innerText = labelText ?? GetDefaultLabelText(html, expression, htmlFieldName); 
     if (string.IsNullOrEmpty(innerText)) 
     { 
      return MvcHtmlString.Empty; 
     } 
     tag.SetInnerText(innerText); 

     // set for attribute 
     string forId = GenerateTextBoxId(tag, html, htmlFieldName); 
     tag.Attributes.Add("for", forId); 

     return MvcHtmlString.Create(tag.ToString(TagRenderMode.Normal)); 
    } 

    /// <summary> 
    /// Extracted from System.Web.Mvc.Html.InputExtensions 
    /// </summary> 
    private static string GenerateTextBoxId<TModel>(TagBuilder tagBuilder, HtmlHelper<TModel> html, string htmlFieldName) 
    { 
     string fullName = html.ViewContext.ViewData.TemplateInfo.GetFullHtmlFieldName(htmlFieldName); 
     tagBuilder.GenerateId(fullName); 
     string forId = tagBuilder.Attributes["id"]; 
     tagBuilder.Attributes.Remove("id"); 
     return forId; 
    } 

    /// <summary> 
    /// Extracted from System.Web.Mvc.Html.LabelExtensions 
    /// </summary> 
    private static string GetDefaultLabelText<TModel, TValue>(HtmlHelper<TModel> htmlHelper, Expression<Func<TModel, TValue>> expression, string htmlFieldName) 
    { 
     var metadata = ModelMetadata.FromLambdaExpression(expression, htmlHelper.ViewData); 
     string labelText = metadata.DisplayName ?? metadata.PropertyName ?? htmlFieldName.Split('.').Last(); 
     return labelText; 
    } 
} 
+0

Итак, в вашем методе, что произойдет, если htmlFieldName содержит квадратные скобки? например «Пользователи [0]» –

+0

Html.LabelForCollectionItem (x => x.Users [0] .Name) возвращает

+0

Это интересный способ сделать это, помог мне подняться с решением для нашей конкретной ситуации. Благодаря! (Я бы проголосовал за ваш ответ, если вы можете отредактировать его - так что обойдусь глупыми правилами stackoverflow) –

 Смежные вопросы

  • Нет связанных вопросов^_^