2011-12-05 24 views
19

Có thể tùy chỉnh phương thức Html.ValidationMessageFor để nó tạo ra HTML khác nhau không?Cách tùy chỉnh Html.ValidationMessageFor trong ASP MVC

tôi muốn làm một cái gì đó tương tự như:

<div class="field-error-box"> 
    <div class="top"></div> 
    <div class="mid"><p>This field is required.</p></div> 
</div> 

Trả lời

24

Tôi không chắc chắn nếu nó có thể sử dụng p aragraph thay vì mặc định span, vì nó có thể làm cho không thể cho val plugin định vị để đặt thông báo lỗi. Nhưng đối với div -s, thats easy - bạn có thể viết helper html tùy chỉnh.

Nội dung nào đó dọc theo các dòng này (có thể cần kiểm tra/mã hóa thêm). Bạn sẽ cần phải bao gồm không gian tên của phương thức mở rộng tĩnh này trong chế độ xem của bạn hoặc đặt trực tiếp vào số System.Web.Mvc.Html.

public static class Validator 
{ 
    public static MvcHtmlString MyValidationMessageFor<TModel, TProperty>(this HtmlHelper<TModel> helper, Expression<Func<TModel, TProperty>> expression) 
    { 
     TagBuilder containerDivBuilder = new TagBuilder("div"); 
     containerDivBuilder.AddCssClass("field-error-box"); 

     TagBuilder topDivBuilder = new TagBuilder("div"); 
     topDivBuilder.AddCssClass("top"); 

     TagBuilder midDivBuilder = new TagBuilder("div"); 
     midDivBuilder.AddCssClass("mid"); 
     midDivBuilder.InnerHtml = helper.ValidationMessageFor(expression).ToString(); 

     containerDivBuilder.InnerHtml += topDivBuilder.ToString(TagRenderMode.Normal); 
     containerDivBuilder.InnerHtml += midDivBuilder.ToString(TagRenderMode.Normal); 

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

Như bạn thấy, điều này sử dụng phương thức mặc định ValidationMessageFor để không can thiệp vào quá trình xử lý thông báo lỗi xác thực-plugin.

Và bạn sử dụng này đơn giản, như xác nhận mặc định helper nhắn

@Html.MyValidationMessageFor(model => model.SomeRequiredField) 
+0

Đây chỉ là những gì tôi đang tìm kiếm. Tôi chưa hiểu vấn đề với plugin xác thực, nhưng tôi sẽ xem xét vấn đề đó. Cảm ơn! – parleer

+3

Điều này làm việc tốt cho tôi, nhưng hãy chắc chắn để khai báo lớp trợ giúp tĩnh của bạn trong không gian tên System.Web.Mvc.Html và nó sẽ làm việc thực sự tốt. –

+1

Làm cách nào để bạn thực sự thay đổi html được tạo bởi thông báo 'ValidationMessageFor'. Tôi không nói về gói nó trong div khác. Có thể không? –

-2

Vâng, chỉ cần sử dụng một metamodel cho lĩnh vực này:

[MetadataType(typeof(YourMetaData))] 
public partial class YOURCLASS 
{ 
    [Bind(Exclude = "objID")] 
    public class YourMetaData 
    { 
     [Required(AllowEmptyStrings = false, ErrorMessage = "Please enter a name")] 
     public object Name { get; set; } 
    } 
} 

Thay đổi thông điệp của bạn ở lĩnh vực ErrorMessage :) Hope trợ giúp này:)

+0

Anh ấy muốn html tùy chỉnh, chứ không phải thông báo lỗi tùy chỉnh – archil

+0

opps, tôi đoán tôi hiểu sai – shennyL

3

Bạn có thể thực hiện helper ValidationMessageFor của riêng bạn để phát ra đầu ra mong muốn của bạn hoặc sử dụng một số javascript để thêm/sửa đổi mã HTML rendered nhưng tùy chỉnh ValidationMessageFor thực hiện là cách tiếp cận sạch hơn IMHO.

Để triển khai trình trợ giúp ValidationMessageFor của riêng bạn, hãy xem các phương thức ValidationExtensions.ValidationMessageFor và ValidationMessageHelper trong mã nguồn ASP.NET MVC.

thực hiện gợi ý

Kể từ GetFormContextForClientValidation là nội bộ, bạn phải làm việc xung quanh thực hiện điều đó bằng cách sao chép các chức năng nội bộ trong mã của bạn:

FormContext formContext = htmlHelper.ViewContext.ClientValidationEnabled ? htmlHelper.ViewContext.FormContext : null; 

Một số phương pháp khác là tư nhân trong ValidationExtensions như GetUserErrorMessageOrDefault bạn sẽ cũng cần phải lặp lại mã đó. Những gì bạn có thể làm để tránh trùng lặp mã là để ValidationExtentensions.ValidationMessageFor trả về chuỗi thông báo xác thực được gói trong một khoảng và sau đó thay đổi chuỗi được hiển thị theo yêu cầu của bạn. Hãy nhớ rằng "null" được trả lại trong trường hợp không tìm thấy lỗi và bạn sẽ cần các thuộc tính HTML dữ liệu trong trường hợp bạn đã bật JavaScript không phô trương.

Bạn có thể tải về mã nguồn ASP.NET MVC 3 từ here

2

Nhu cầu chỉ cho sự thay đổi của thế hệ thẻ mặc định là trong trường hợp của tôi, kéo dài kết quả hành vi trong anoying thiết lập lề.

Tôi đã giải quyết vấn đề này bằng cách sử dụng 'display: block'

Có thể điều này sẽ giúp một số người ..

7

tôi đã sử dụng một cách khác:

public static MvcHtmlString DivValidationMessageFor<TModel, TProperty>(this HtmlHelper<TModel> htmlHelper, Expression<Func<TModel, TProperty>> expression) 
    { 
     return MvcHtmlString.Create(htmlHelper.ValidationMessageFor(expression).ToString().Replace("span", "div")); 
    } 

Bằng cách này bạn có thể sử dụng được xây dựng theo cách, nhưng thay thế nhịp với một div.

Nếu bạn cần bất kỳ tình trạng quá tải nào khác của chức năng, chỉ cần sao chép khi cần thiết.

+0

Tôi thích phương pháp này. Dễ dàng hơn nhiều so với việc sao chép tất cả mã ValidationMessageHelper cho một thay đổi nhỏ như vậy. –

+0

Hy vọng bạn không xác thực ngày giữa hai lần .. – user2864740

0

Có lẽ bạn có thể đặt mã

string propertyName = ExpressionHelper.GetExpressionText(expression); 
string name = helper.AttributeEncode(helper.ViewData.TemplateInfo.GetFullHtmlFieldName(propertyName)); 

if (helper.ViewData.ModelState[name] == null || 
    helper.ViewData.ModelState[name].Errors == null || 
    helper.ViewData.ModelState[name].Errors.Count == 0) 
    { 
     return MvcHtmlString.Empty; 
    } 

trên đầu trang của các chức năng trả lời, do đó div không xuất hiện trên các tải mẫu đơn.

Các vấn đề liên quan