The principle of loading web user controls dynamically is easy, that is to use the
PlaceHolder control. However, it is not easy to make dynamically loaded controls to work properly if we miss some key points. Detailed information about how to use web user controls dynamically is introduced in this article.
Firstly, remember to use the
LoadControl method instead of just creating a new instance of the web user control. Using the
new operator to create the instance of the web user control won't work because it just creates the control itself. All the child controls in the created web user control won't be initialized, as we can see in the following figure:
In the example above, the
HelloWorld web user control contains a button (
btnSayHello), a label (
lblHello), a required field validator (
rfv), and a text box (
txtName). We can see that after
HelloWorld has been created, no control within it is initialized.
So use the
Page.LoadControl method instead of the
new operator. The following figure shows the value of the members in the created control, which is much different from the ones we got previously.
After getting the control instance that is returned by the
Page.LoadControl method, we can now use the
PlaceHolder to render the control. The following line shows how:
Now you can render the control properly on the page. But what's next? When you want to fire server events in your loaded web user control, you'll find that everything is gone! The control totally disappears when the page is posted back.
What happens? Actually, ASP.NET pages run in the server environment, and it is a stateless object. This means once the page is generated for the client, the instance is disposed. So if we define a local variable in the page object, we cannot get its pervious value when the page is posted back because the page object is pretty new other than the one we first worked with.
In order to correctly render the control even if the page is posted back from the server, we must persist the control so that it can be re-rendered when the page is initializing or loading. It is impossible to persist the entire web user control with the view state or session because the web user control is not serializable. We can persist the virtual path of the control instead, so that the control can be recreated once the proper page events are fired. Don't worry about the state of the fields within the control, they will be maintained by the control itself.
Now we have the steps for loading and using web user controls dynamically. We can follow these steps which are briefly described below (for detailed solutions, please refer to the attached source files).
- Implement a private property for saving and retrieving the saved virtual path of the web user controls.
- Implement a private method for creating and loading the web user control according to the saved virtual path. It is important to remember to set the ID for the control; otherwise, the page won't work properly.
Page_Load event, simply call the method we created in step 2 to recreate the control.
- In the
Button_Click event, set the private property we created in step 1 to the virtual path of the control that needs to be created and loaded; then call the method we created in step 2 to recreate and load the control.
- Override the
Dispose method and dispose the controls.