asp.net在回發后動態添加用戶控件保存值

[英]asp.net dynamically added user control saving values after postback


Here's my issue. I have a usercontrol that I want to allow users to add as many instances of as necessary using a button click (each time a button is clicked, I want to add another instance of my user control to a Panel). It works fine the first time, but each additional post back removes all of the added controls. I have no problem keeping track of the number of user controls a user has added but how do I ensure they stay in the same state they were before the postback? I've read some posts about people using SaveViewState and LoadViewState but I haven't been able to find any examples.

這是我的問題。我有一個usercontrol,我希望允許用戶使用按鈕單擊添加任意數量的實例(每次單擊一個按鈕,我想將另一個用戶控件實例添加到Panel)。它第一次工作正常,但每個額外的回發刪除所有添加的控件。我跟蹤用戶添加的用戶控件的數量沒有問題,但我如何確保它們保持在回發之前的狀態?我已經閱讀了一些關於使用SaveViewState和LoadViewState的人的帖子,但我找不到任何例子。

My biggest issue is ensuring that all of the text boxes and dropdownlists from each user control stays populated with the same text/selected value/data after each post back

我最大的問題是確保每個用戶控件的所有文本框和下拉列表在每個回發后都保持填充相同的文本/選定值/數據

Thanks in advance, Ben

提前謝謝,本

7 个解决方案

#1


10  

Since you're programmatically adding controls to your page, you'll need to recreate them on EACH postback.

由於您是以編程方式向頁面添加控件,因此您需要在每次回發時重新創建它們。

Also, it's necessary that you recreate programmatically added controls on PreInit or Init event of the page. This is for proper viewstate restoring event management.

此外,您必須在頁面的PreInit或Init事件上重新創建以編程方式添加的控件。這適用於正確的視圖狀態恢復事件管理。

If you don't do this, control will be gone on postback and they won't handle any event.

如果你不這樣做,控制將在回發時消失,他們將不會處理任何事件。

EDIT

Although is recommended to add dynamically controls on PreInit or Init it's true (as Dustin Hodges says) that it may work if you add them on page_load. I'd say you should avoid it unless you have no other option.

雖然建議在PreInit或Init上添加動態控件,但是如果你在page_load上添加它可能會有效(如Dustin Hodges所說)。除非你別無選擇,否則你應該避免它。

You may be able to get away with loading your controls in the Page_Load event handler and maintaining the view state properly.
It all depends on whether or not you are setting any properties of the dynamically loaded controls programmatically and, if so, when you're doing it relative to the Controls.Add(dynamicControl) line.
A thorough discussion of this is a bit beyond the scope of this article, but the reason it may work is because the Controls property's Add() method recursively loads the parent's view state into its children, even though the load view state stage has passed.

您可以在Page_Load事件處理程序中加載控件並正確維護視圖狀態。這完全取決於您是否以編程方式設置動態加載控件的任何屬性,如果是,則相對於Controls.Add(dynamicControl)行進行此操作。對此的深入討論有點超出了本文的范圍,但它可能起作用的原因是因為Controls屬性的Add()方法以遞歸方式將父視圖狀態加載到其子節點中,即使已經過了加載視圖狀態階段。

Source MSDN

#3


2  

If you are keeping track of the number of controls the user has added you need to recreate the controls the user added previously, preferably in Page_Init or Page_Load. Add something like this to that handler:

如果要跟蹤用戶添加的控件數量,則需要重新創建用戶之前添加的控件,最好是在Page_Init或Page_Load中。將這樣的內容添加到該處理程序:

for(int i=0; i<NumberOfControlsUserHasAdded; i++)
{
    //todo:  change this to the appropriate user control
    TextBox tb = new TextBox();
    tb.ID = "tb" + i.ToString();
    //todo:  add to appropriate control collection
    this.Controls.Add(tb);
}

If you do it this way, the state of the controls should be maintained because when you add the tb control to a controls collection it plays catch up with events and should automagically restore its viewstate.

如果你這樣做,應該保持控件的狀態,因為當你將tb控件添加到控件集合時,它會捕獲事件並應自動恢復其viewstate。

You shouldn't have to keep track of their state in session as in most cases it will be stored in the viewstate for you

您不必在會話中跟蹤其狀態,因為在大多數情況下,它將存儲在視圖狀態中

#4


1  

I had a nightmare of a time trying to pull this off on an old project. In the intermediate time, I've discovered that I know a lot less about web development than I thought (reading this website is a great way to humble yourself on a daily -- if not hourly -- basis). In that project, Page.IsPostBack was totally useless to me because I had dynamically instantiated the controls.

我有一個噩夢,試圖在一個舊項目上解決這個問題。在中間階段,我發現我對網絡開發的了解遠遠少於我的想法(閱讀這個網站是一個很好的方式來謙卑自己每天 - 如果不是每小時 - 基礎上)。在那個項目中,Page.IsPostBack對我來說完全沒用,因為我已經動態地實例化了控件。

That being said, the best thing I can suggest is to consider using the Session variable. If you have a class (or a collection of a class) that represents the data you capture from the page, then perhaps it'd be easiest to store values in that class/collection to improve code readability, and then write it out to the Session.

話雖這么說,我建議的最好的事情是考慮使用Session變量。如果你有一個類(或類的集合)代表你從頁面捕獲的數據,那么也許最容易在該類/集合中存儲值以提高代碼可讀性,然后將其寫入會話。

#5


0  

Look at your PageLoad and add if(!this.IsPostBack) before the line where you clear the panel.

查看您的PageLoad並在清除面板的行之前添加if(!this.IsPostBack)。

this is of course just a guess, but I have seen many questions where the problem was related to this.

這當然只是一個猜測,但我已經看到很多問題,問題與此有關。

#6


0  

I think what may be happening is when you click the button to add, Page_Load fires which creates you a brand new page. Then, the button click method adds the control and the page finishes rendering. When you click it the second time, Page_Load creates your page and the button click method again creates a control and adds it to the page. Unfortunately, the one you added previously is no longer there.

我認為可能發生的事情是當你點擊按鈕添加,Page_Load fires會為你創建一個全新的頁面。然后,按鈕單擊方法添加控件,頁面完成渲染。當您第二次單擊它時,Page_Load會創建您的頁面,再次按鈕單擊方法會創建一個控件並將其添加到頁面中。不幸的是,你之前添加的那個不再存在。

What if you added the controls to a Repeater? The Repeater's view state may keep track of each control you add so that on post-back, it's not blown away.

如果您將控件添加到Repeater會怎樣? Repeater的視圖狀態可以跟蹤您添加的每個控件,以便在回發后,它不會被吹走。

#7


0  

It's an ugly solution if you have a ton of users, but you could stick the usercontrols themselves into the session. I do this with my footer control because I don't want to hit the db every time the page changes to recreate the footer.

如果您有大量用戶,這是一個丑陋的解決方案,但您可以將用戶控件自己粘貼到會話中。我使用頁腳控件執行此操作,因為每次頁面更改以重新創建頁腳時我都不想訪問數據庫。

This solutions can get really tasking on the server if you have a lot of users and they use this feature a lot. At least I think it will...

如果您擁有大量用戶並且他們使用此功能,則此解決方案可以在服務器上獲得真正的任務。至少我認為它會......

But you can just repopulate your placeholder that has the usercontrols in it on page_load. I can put up an example shortly.

但是你可以在page_load上重新填充其中包含usercontrols的占位符。我可以很快提出一個例子。

Example of what I do:

我做的例子:

if (Session["footer"] == null)
{
 Session["footer"] = new Footer(LinksRules.BuildFooterLinks((int)WebSiteSections.Main));// where Footer is my control
}
footerPH.Controls.Add((Footer)Session["footer"]);

Like a singleton pattern sort of...

像單身模式一樣......

So as I see it you could do this on anything that will cause a postback

因此,我認為你可以在任何會導致回發的事情上做到這一點

Session["DynamicControls"] = PlaceHolder.Controls;

Session [“DynamicControls”] = PlaceHolder.Controls;

and in the page-Load method you could:

在頁面加載方法中,您可以:

foreach(var control in (List<Controls>)Session["DynamicControls"])
{
  yourPlaceHolder.Controls.Add(control);
}

and if the session object is null just add a single one like they've never been there..

如果會話對象為null,只需添加一個就像他們從未去過那里一樣。

I believe this will hang on to the data inside the controls like you want.

我相信這會像你想要的那樣依賴於控件內部的數據。


注意!

本站翻译的文章,版权归属于本站,未经许可禁止转摘,转摘请注明本文地址:https://www.itdaan.com/blog/2010/10/15/33d5ba72c105e29c38fef724723e506f.html



 
  © 2014-2022 ITdaan.com 联系我们: