Create Composite Control using Ajax Toolkit Controls






4.67/5 (4 votes)
How to create a Composite Control containing the features of Ajax ResizableControlExtender, CollapsiblePanelExtender and DragPanelExtender
Introduction
Ajax Control Toolkit allows the developer to create Web applications that can update data on the Web page without a complete reload of the page, and contain many controls with very interesting features: popup panels, resizable controls, floating controls and others.
Often you want a control with some features of some other controls, so you can achieve the goal of joining more controls in a single control as CompositeControl
.
Composite Controls are controls that combine multiple controls together to form a new reusable control. For example, I want to create a control container that makes resizable, collapsible, draggable all guest controls as IFrame
or others.ResizableControlExtender
, CollapsiblePanelextender
, DragPanelExtender
controls extend their own features to the Panel
written on TargetControlID
property so you can create a mix like this:

Background
This is a graphic representation of the control...

... and this is the code, built in the page, of the control described in the bitmap above.
<%--====== StyleSheet class needed by the control build in page ====--%>
...
<%-- PANEL CONTAINER --%>
<asp:Panel ID="PanelContainer" runat="server" Visible="false"
style="Left:200px; Position:absolute; Top:100px;">
<%-- PANEL CLOSE --%>
<asp:Panel ID="PanelClose" runat="server" Height="20px">
<asp:ImageButton ID="ImageButton1"
runat="server" style="cursor: hand"
ImageAlign="Right" Height="100%" ImageUrl="~/images/close.gif"
onclick="ImageButton1_Click" />
</asp:Panel>
<%-- PANEL HEADER --%>
<asp:Panel ID="PanelHeader" runat="server" style="cursor: hand" Height="20px"
BackImageUrl="~/images/RoundedGrayExplorer.gif">
</asp:Panel>
<%-- PANEL BODY --%>
<asp:Panel ID="PanelBody" runat="server" BorderStyle="Solid" BorderWidth="1px">
<iframe id="ieframe" scrolling="auto" runat="server"
src="HTMLPage.htm"
height="100%"
width="100%">
</iframe >
</asp:Panel>
</asp:Panel>
<%--====== AjaxPanelExtender Controls ============================--%>
...
<%--====== Client side script needed to the behavior ====--%>
...
Now we will convert it in a redistributable Composite Control.
Using the Code
In order to test the control build in the page, set AjaxCompositePanelBuildInPage.aspx as the project start page.
In order to test the composite control, set AjaxCompositePanelBuildInControl.aspx as the project start page.
Points of Interest
A composite control class AjaxCompositePanel
inside AjaxCompositePanel.cs file inherits from the CompositeControl
class, and has some class attributes...
//This attribute gives to the control added on Visual Studio Toolbox
//the icon of other control,View control in this case.
[ToolboxBitmap(typeof(View))]
//This attribute sets a control name displayed on the toolbox of Visual Studio.
[ToolboxData("<{0}:AjaxCompositePanel runat="server">")]
//This attribute sets a design-time rendering support class.
[Designer("AjaxCompositePanelControl.AjaxCompositePanelDesigner")]
public class AjaxCompositePanel : CompositeControl
{
...
... and some method attributes for design-time behaviors inside Visual Studio properties window:
//Visible from Visual Studio properties windows.
[Browsable(true)]
//Property category
[Category("AjaxCompositePanel")]
//Property default value displayed on properties windows
[DefaultValue("")]
//Property description
[Description("Url of header image.")]
[Localizable(true)]
[RefreshProperties(RefreshProperties.Repaint)]
//Support to design time editors as select files URL or select color.
[UrlProperty]
[EditorAttribute(typeof(System.Web.UI.Design.ImageUrlEditor),
typeof(System.Drawing.Design.UITypeEditor))]
public string BarImageUrl
{
...
The main method of Custom Control is method named CreateChildControls
which can be overridden, that calls CreateControlsHierarchy()
within which a tree structure of the child control is built and added to the controls collection:
protected virtual void CreateControlsHierarchy()
{
...
//Create and set PanelContainer.
Panel DragebleResizablePanelContainer = new Panel();
DragebleResizablePanelContainer.ID = "DragebleResizablePanelContainer";
DragebleResizablePanelContainer.Visible = false;
DragebleResizablePanelContainer.Attributes["style"] = "float: right";
//Create and set PanelHeader.
Panel DrageblePanelHeader = new Panel();
DrageblePanelHeader.ID = "DrageblePanelHeader";
DrageblePanelHeader.Attributes["style"] = "cursor: hand";
//Adds PanelHeader as child to the PanelContainer controls collection.
DragebleResizablePanelContainer.Controls.Add(DrageblePanelHeader);
//Adds PanelContainer to the controls collection of composite control.
Controls.Add(DragebleResizablePanelContainer);
...
Composite Control client side behavior will need JavaScript methods that will be added to the page...
//Adds a script block to the top of the page.
if (!Page.ClientScript.IsClientScriptBlockRegistered("clientScript"))
{
System.Text.StringBuilder sb = new System.Text.StringBuilder();
sb.Append("<script type="\"text/javascript\""></script>");
Page.ClientScript.RegisterClientScriptBlock(this.GetType(),
"clientScript", sb.ToString(),false);
}
//Adds a script block into the page that executes when the page
//finishes loading but before the page's onload event is raised.
if (!Page.ClientScript.IsStartupScriptRegistered("repositioningScript"))
{
//Page.ClientScript.RegisterStartupScript(this.GetType(),
//"clientScript", sb.ToString(), false);
}
... and also a stylesheet class used for Ajax Panel Extender will be added to the page:
protected virtual void CreateControlsHierarchy()
{ ...
//Adds to the page header a stylesheet class
this.Page.Header.StyleSheet.CreateStyleRule(new ResizingIFrameCssClass(),
this.Page, ".resizingIFrame");
...
}
...
// Stylesheet class
class ResizingIFrameCssClass : Style
{
protected override void FillStyleAttributes
(CssStyleCollection attributes, IUrlResolutionService urlResolver)
{
base.FillStyleAttributes(attributes, urlResolver);
attributes[HtmlTextWriterStyle.Padding] = "0px";
attributes[HtmlTextWriterStyle.BorderStyle] = "solid";
attributes[HtmlTextWriterStyle.BorderWidth] = "2px";
attributes[HtmlTextWriterStyle.BorderColor] = "#B4D35D";
}
}
At the end, only one word on Design-Time rendering of the control.
Inside AjaxCompositePanelDesigner.cs, you can see the AjaxCompositePanelDesigner
class that inherits from the CompositeControlDesigner
class, and GetDesignTimeHtml
method which can be overridden that retrieves the HTML markup used to render the control at design time.
History
- 28th November, 2008: Initial version