Introduction:
If you haven't read my previous article1,
I would recommend doing so prior to reading this one, as it builds upon the
foundations laid out in that article. Because ASP.Net is object-oriented and
event-driven, the various events and execution of a Server Control can get a
bit confusing. This article takes you through the Lifecycle of a Server
Control and explains exactly what is happening at each stage of it's
existence.
What is a Server Control?
In ASP.Net, any class which can render an HTML interface in an ASPX page
(i.e. write HTML to the output stream) is classified under the
Namespace System.Web.UI.Control. This includes the Page class,
Literal Controls, HTML Controls, Web Controls, User
Controls, and Custom Controls. This means that all Server
Controls inherit System.Web.UI.Control. That means that all Server
Controls have certain properties,
methods, and events
in common. Let's take a look:
Control Properties:
-
ClientID - The ClientID is the "ID" attribute assigned to the HTML
object which this Control represents in the page. It is used for
client-side operations such as JavaScript functions. As any Server Control
which can maintain state and do PostBacks must have a client side HTML
"ID" attribute in order to use the JavaScript state and event management
client-side functions, this property automatically supplies one if the
developer does not.
- Controls
- This is a Collection of the Controls contained inside this one.
Like a Windows Form, an ASPX page can host multiple Controls, and is,
in fact, a Control. In practical terms, a Control is contained inside
another control if the HTML for the control is between the beginning and
ending tags of another HTML Control. Example:
<form id="Form1" method="POST" runat="server">
<asp:label id="Message1" font-size="16" font-bold="true" forecolor="red"
runat=server>This is Message One</asp:label>
</form>
In the example above, the Label WebControl is a member of the Controls
Collection of the Form HTMLControl.
- EnableViewState
- This Boolean value indicates whether or not the Control should
"remember" it's state between PostBacks1.
- ID
- This can be a bit confusing, as it looks a lot like
ClientID. The ID property is used on the
server-side to access the Control programmatically (in the CodeBehind
class).
-
NamingContainer - This property
references the parent Control of this Control and implements the
iNamingContainer Interface. The purpose of the iNamingContainer
Interface is to make sure that the ID property of all
Controls is unique. Any Control contained in a Control which implements
iNamingContainer will have a Unique ID regardless
of whether it has the same ID as another Control. The
ID is derived from the assigned ID and
the ID of the parent Container.
- Page
- This property references the Page object in which this Control resides.
- Parent - This
property references the Control which immediately contains this one in
it's hierarchy of containers.
- Site - This
property contains information about the Control's Web Site.
-
TemplateSourceDirectory -
returns the virtual directory of the Page or User Control which contains
the Control.
-
UniqueID - Returns the unique, hierarchically-qualified ID of the
Control. This is different from ID and
ClientID, in that multiple Controls can have the
same ID, but not the same UniqueID. When hosted inside a
NamingContainer, the UniqueID is a
combination of the ID of the
NamingContainer and the ID of the Control.
- Visible - This
Boolean value indicates whether or not the control will be rendered in the
page. When set to False, no HTML for the Control (or any child controls
contained therein) will appear in the Page.
Control Methods
- DataBind - Binds
data from a Data Source to a Server Control. This method is used most
often with templated data-bound Controls.
- Dispose - Frees
up resources used by a Control when it is no longer needed.
- Equals
(inherited from Object) - Used to determine whether 2 object
instances are equal.
- FindControl -
Searches the current naming container for a specific Control
- GetHashCode
(inherited from Object) - Returns a type-specific hash code for an
Object
- GetType
(inherited from Object) - Returns a System.Type object with
Type metadata regarding that Type
- HasControls -
This method returns a Boolean value that indicates whether the Control
contains other Controls
- RenderControl -
This is the method which writes the HTML for the Control to the output
stream.
- ResolveUrl -
This method resolves a relative URL to an absolute URL, according to the
TemplateSourceDirectory
property.
- ToString
(inherited from Object) - This method returns a string that
represents this Object.
Control Events
Because HTTP is stateless,
a Server Control has a very short lifetime. It exists from the time
the Page is requested until the Page is sent to the browser, at which time
the Page, and its' entire contents, are disposed of. During this lifetime,
the control must be re-instantiated and started first. Then Events from the
client browser can be processed by the control. Finally, all controls in a
Page render their HTML, and the Page does it's clean-up. At any point in
that LifeCycle, the developer may want to add code to do something.
Therefore, the various "insertion points" for code are made available via a
number of Events which fire during a Control's lifetime:
- Init - This
event occurs as the control is being instantiated.
- LoadViewState -
Once all controls are instantiated, the ViewState can be loaded for each
control. This is handled automatically, and is used to maintain state of
controls which can do so. As you should recall from my first article1,
ViewState is maintained on the client in a hidden form field. The Control
reads the hidden "__VIEWSTATE" field's data from the form, and loads the
ViewState data from the last Request into the ViewState object
(Collection) on the server.
-
LoadPostData (if iPostBackDataHandler
is implemented for this Control) - The control processes PostBack data,
and updates its' properties accordingly. The LoadPostData Sub takes 2
arguments: The PostDataKey and the PostCollection. The
PostDataKey (string) contains the ID of the Control which caused the
PostBack. The PostDataCollection is similar to the Request.Form
Collection; it contains all the data posted from the form. This Sub is
used to do any post data processing that may be necessary at this point.
It returns a Boolean value. If it returns True, the
RaisePostDataChangedEvent is
fired.
- Load - This
Event Handler performs functions that are common to all requests -
generally where the "meat" of your code usually goes. The controls have
now been initialized. ViewState has been restored, and the state of the
controls is now as it was on the client.
-
RaisePostDataChangedEvent (if
iPostBackDataHandler is implemented for this Control) - This event
is raised when the LoadPostData Sub returns
True. It is generally usually used to raise any events from the Control
that need to be fired as a result of Post Data changing.
- RaisePostBackEvent
(if iPostBackEventHandler is implemented for this Control) - This
event is used by Server Controls which process PostBack events coming
from Server Controls. Notice that this event occurs just after
the RaisePostDataChangedEvent.
That is so that any
RaisePostDataChangedEvents can be fired first, allowing other Controls
to react to them in this Event Handler.
- PreRender - This
Event Fires just before the SaveViewState method is called. It can be used
to make any changes to the control which will still be needed for the
current Request, and must be made after handling PostBack events.
At this point, the Control is ready to be rendered (written) to the HTML
output stream.
- SaveViewState -
This Method writes the new (modified) ViewState value to the output
document's hidden "__VIEWSTATE" field.
- Render - This
Method writes the HTML output of the Control to the output stream.
- Dispose -
Perform any final cleanup prior to unloading.
- Unload - Fires
just prior to the Control unloading.
Conclusions: As HTTP is stateless,
Server Controls have a very short lifetime. To the user, they see the same
HTML interface with each PostBack, and it looks as if they are working with
the same Controls with each Page refresh. In truth, however, Server Controls
must be rebuilt with each request, and put into their last state prior to
processing PostBack data, and performing any new operations.
Understanding the sequence
of Events that occur within the LifeCycle of a Server Control is important
to writing effective ASP.Net applications. |