2009-10-16 19 views
10

Tôi có một trang có nhiều điều khiển người dùng trên đó. Tôi muốn có thể có "macro" hoặc "trình giữ chỗ" trực tiếp trong nội dung sẽ được thay thế trong mã của tôi. Nó không thực sự quan trọng, nhưng tôi đang sử dụng Ektron làm CMS của tôi.Làm thế nào tôi có thể sửa đổi toàn bộ nội dung trang ASP.NET ngay trước khi đầu ra của nó?

Có bất kỳ sự kiện trang nào mà tôi có thể móc vào để thực hiện chuỗi thay thế trên toàn bộ nội dung trang được hiển thị, ngay trước khi nó được gửi cho khách hàng không?

CẬP NHẬT

Đây là mã mà tôi hiện đang sử dụng để thực hiện điều này:

protected override void Render(HtmlTextWriter writer) 
{ 
    string content = string.Empty; 

    using (var stringWriter = new StringWriter()) 
    using (var htmlWriter = new HtmlTextWriter(stringWriter)) 
    { 
     // render the current page content to our temp writer 
     base.Render(htmlWriter); 
     htmlWriter.Close(); 

     // get the content 
     content = stringWriter.ToString(); 
    } 

    // replace our placeholders 
    string newContent = content.Replace("$placeholder1$", "placeholder1 data").Replace("$placeholder2$", "placeholder2 data"); 

    // write the new html to the page 
    writer.Write(newContent); 
} 

Trả lời

8

Các bạn đã thử cách ghi đè các phương pháp render?

protected override void Render(HtmlTextWriter writer) 
{ 
    StringBuilder htmlString = new StringBuilder(); // this will hold the string 
    StringWriter stringWriter = new StringWriter(htmlString); 
    HtmlTextWriter tmpWriter = new HtmlTextWriter(stringWriter); 
    Page.Render(tmpWriter); 
    writer.Flush(); 

    writer.Write(DoReplaceLogic(htmlString.ToString());); 
} 
+0

Có, đây là địa điểm phù hợp nhưng có thể (và khôn ngoan) để đặt lại và đọc luồng không? –

+1

bạn sẽ không bao giờ "đặt lại" luồng vì luồng này chưa được gửi. Tôi không chắc chắn nếu khôn ngoan của nó, không, tôi chỉ trả lời câu hỏi lol – JustLoren

+0

Tôi đang sử dụng phương pháp này ngay bây giờ, nhưng sẽ chờ đợi để chấp nhận câu trả lời để xem nếu có một giải pháp tốt hơn. Về cơ bản, tôi ... Cho phép trang ghi vào bộ đệm tạm thời. Sửa đổi bộ đệm. Thay bộ đệm gốc bằng bộ đệm đã sửa đổi. –

1

Bạn đã xem sự kiện PreRender trong vòng đời chưa?

Trước khi sự kiện này xảy ra:

• Trang Đối tượng gọi EnsureChildControls cho từng kiểm soát và cho trang.

• Mỗi kiểm soát ràng buộc dữ liệu có thuộc tính DataSourceID được đặt là phương thức DataBind .

• Sự kiện PreRender xảy ra cho mỗi điều khiển trên trang. Sử dụng sự kiện để thực hiện các thay đổi cuối cùng đối với nội dung của trang hoặc điều khiển của trang.

Tôi tin rằng đây là nơi cuối cùng bạn có thể làm điều gì đó như thế này. Sự kiện tiếp theo là SaveStateComplete, mà theo các tài liệu có hành vi này:

Trước khi sự kiện này xảy ra, ViewState đã được lưu cho trang và cho tất cả các điều khiển. Mọi thay đổi đối với trang hoặc điều khiển tại thời điểm này sẽ bị bỏ qua. Sử dụng sự kiện này thực hiện các tác vụ yêu cầu trạng thái xem để được lưu, nhưng không thực hiện bất kỳ thay đổi nào đối với điều khiển .

0

Câu trả lời đơn giản mà bạn nghĩ đến là sử dụng asp: Điều khiển văn bản cho "trình giữ chỗ" của bạn. Bạn có thể đặt nội dung của họ trong khi tải trang hoặc bạn có thể móc vào sự kiện PreRender và đặt chúng sau đó.

+0

Thật không may, tôi không thể làm điều đó bởi vì những "trình giữ chỗ" này sẽ nằm bên trong nội dung được hiển thị bên trong điều khiển người dùng mà tôi không thể chạm vào. Vì vậy, vào thời điểm nó được cho tôi, điều duy nhất tôi có thể hy vọng làm là nhìn vào nội dung trả lại. –

+0

Xin lỗi, tôi đã bỏ lỡ "điều khiển người dùng", xấu của tôi. Điều khiển người dùng cũng có các sự kiện PreRender. Bạn có thể đặt các thuộc tính công khai trên các điều khiển người dùng của mình mà trang có thể đặt, sau đó có các điều khiển người dùng thực hiện thay thế. –

0

Có vẻ như bạn có thể muốn có các chữ HTML trong trang của mình và sau đó bạn có thể thay thế chúng bằng nội dung thích hợp trên sự kiện Page_Load.

Điều này sẽ yêu cầu bạn viết mã HTML, trái ngược với một số văn bản đơn giản, nhưng có vẻ như bạn có thể đang tiêm mã JavaScript của chính bạn hoặc nội dung tương tự vào đó.

5

Tôi biết rằng câu trả lời này sẽ không giúp ích gì vì bạn đã giải quyết xong sự cố này và đã tiếp tục. Điều này chỉ dành cho những người sẽ đối mặt với một vấn đề tương tự trong tương lai;)

Có hai cách tiếp cận bạn có thể sử dụng.

  1. Điều này tương tự như câu trả lời được chấp nhận . Nhưng tôi khuyên bạn nên ghi đè phương thức hiển thị trong một số BasePage và lấy tất cả các mẫu của bạn từ này.

  2. Sử dụng HttpModule hoặc Global.asax và đính kèm một Filter vào đối tượng Response . Đối với tôi, điều này làm cho ý nghĩa thẩm mỹ thêm là vì thuộc tính "Bộ lọc" được cho là giúp bạn lọc đầu ra chính xác là những gì bạn muốn!

BTW, đi đâu với Ektron cho đến nay? Họ đang khiến tôi phát điên vì chắc chắn!

+0

Cảm ơn câu trả lời. Bỏ phiếu cho nỗ lực! Điều BasePage không thực sự là một giải pháp khác, nhưng nhiều hơn một bổ sung cho một chấp nhận. Nhưng ý tưởng hay. Tôi nghĩ bạn nên tạo một lớp BasePage mà tất cả các trang của bạn đều xuất phát từ đó. Hoặc có thể 2-3 tùy thuộc vào loại trang bạn có. Đối với HttpModule và bộ lọc, đó là một tuyệt vời! Một lần nữa, tương tự như các giải pháp được chấp nhận, nhưng logic cho các thay thế sẽ được trích xuất ra khỏi trang. Điều này sẽ là tuyệt vời nếu bạn đang làm thay thế ở nhiều nơi! Tốt đẹp! –

+0

Oh yeah ... Ektron ... Cá nhân tôi không thích nó. Toàn bộ sản phẩm là ass-backwards. API của họ xấu xí và rất phức tạp. Toàn bộ sản phẩm là lỗi, nhưng mã bị làm xáo trộn, do đó bạn không có hy vọng cố gắng tìm ra những gì họ đang cố gắng làm. Diễn đàn hỗ trợ của họ không tốt lắm. Nếu bạn đang tìm kiếm một CMS mới, tôi sẽ giới thiệu Kentico. Đối với hầu hết các phần, bạn không phải viết bất kỳ mã nào. Nhưng khi bạn viết mã, API của họ thật tuyệt vời! Cái kẹp duy nhất mà tôi có với Kentico là hệ thống bộ nhớ đệm của họ gây nhầm lẫn, và theo mặc định, không được thiết lập một cách thông minh. –

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