RadDock PostBackTrigger

17 posts, 0 answers
  1. Allan
    Allan avatar
    10 posts
    Member since:
    Jun 2009

    Posted 23 Jun 2010 Link to this post

    Hi,

    I have a aspx form with a Master Page.  The Master Page has a RadScriptManager.  The form has an UpdatePanel with a RadDockLayout and RadDockZone control.  The logic will dynamically load RadDock controls.  The RadDock controls each have an embedded usercontrol.  The user control has navigation buttons.  I cannot get the click events of the buttons in user control to fire. 

    I figured the solution was to register an AsyncPostBackTrigger event for each button.  I tried to do this in three different ways with no success:

    1)Pass the update panel to the user control.  The user control registers the trigger and adds it to the update panel.  I tried setting the controlid parameter to ID, CLientId and UniqueId.  I get an error stating the the Update panel cannot find the "Control Name" .
    2) Get a reference to the radscriptmanager and use RegisterAsyncPostBackControl to register each button control.  I get no errors, but no click events either.
    3) Provide properties for the client id in the user control.  Register the user control in the form using method #1.  I get the same error as #1 as well.

    Thanks,

    Al Rosner



    Source for ASPX

    <%@ Page Language="C#" AutoEventWireup="true" CodeFile="Home.aspx.cs" Inherits="Home" 
        MasterPageFile="~/loggedIn.master" %> 
     
    <%@ Register TagPrefix="telerik" Namespace="Telerik.Web.UI" Assembly="Telerik.Web.UI" %> 
    <%@ Register Src="~/UserControls/Gadget.ascx" TagName="Gadgets" TagPrefix="uc" %> 
    <asp:Content ID="ContentArea" ContentPlaceHolderID="ContentPlaceHolder1" runat="Server">  
        <asp:UpdatePanel runat="server" ID="UpdatePanel1">  
            <ContentTemplate> 
                <telerik:RadDockLayout runat="server" ID="rdlGadgets" OnSaveDockLayout="rdlGadgets_SaveDockLayout" 
                    OnLoadDockLayout="rdlGadgets_LoadDockLayout">  
                    <telerik:RadDockZone runat="server" ID="rdzGadgets" Orientation="Horizontal" Width="100%" 
                        MinHeight="200" Style="float: left; margin-right: 20px;">  
                    </telerik:RadDockZone> 
                </telerik:RadDockLayout> 
            </ContentTemplate> 
        </asp:UpdatePanel> 
        <br /> 
        <asp:Button ID="btnAdd" runat="server" Text="Add" OnClick="btnAdd_Click" /> 
    </asp:Content> 

    Code Behind for ASPX

    using System;  
    using System.Data;  
    using System.Configuration;  
    using System.Collections;  
    using System.Web;  
    using System.Web.Security;  
    using System.Web.UI;  
    using System.Web.UI.WebControls;  
    using System.Web.UI.WebControls.WebParts;  
    using System.Web.UI.HtmlControls;  
    using Telerik.Web.UI;  
    using System.Collections.Generic;  
     
    public partial class Home : System.Web.UI.Page  
    {  
        private const string _createPage = "CreateGadget.aspx?Id=";  
     
        private List<DockState> CurrentDockStates  
        {  
            get 
            {  
                //Store the info about the added docks in the session. For real life  
                // applications we recommend using database or other storage medium  
                // for persisting this information.  
                //get data  
                DataLayer.toReadGadgetsDataTable gadgets = DataAccess.GetGadgets(Users.GetUserInfo.UserId);  
     
                List<DockState> currentDockStates = new List<DockState>();  
     
                foreach (DataRow dr in gadgets.Rows)  
                {  
                    DataLayer.toReadGadgetsRow row = dr as DataLayer.toReadGadgetsRow;  
     
                    currentDockStates.Add(CreateDockState(row));  
                }  
     
                return currentDockStates;  
            }  
            set 
            {  
                List<DockState> currentDockStates = value;  
     
                foreach (DockState dockState in currentDockStates)  
                {  
                    DockStateTag tag = new DockStateTag(dockState.Tag);  
                    //update gadget in db  
                    DataAccess.UpdateGadget(  
                        int.Parse(dockState.UniqueName),  
                        tag.SearchCriteria,  
                        dockState.Title,  
                        dockState.Index,  
                        tag.DisplayRows  
                        );  
                }  
            }  
        }  
     
        private void CreateSaveStateTrigger(RadDock dock)  
        {  
            //Ensure that the RadDock control will initiate postback  
            // when its position changes on the client or any of the commands is clicked.  
            //Using the trigger we will "ajaxify" that postback.  
            dock.AutoPostBack = true;  
            dock.CommandsAutoPostBack = true;  
     
            AsyncPostBackTrigger saveStateTrigger = new AsyncPostBackTrigger();  
            saveStateTrigger.ControlID = dock.ID;  
            saveStateTrigger.EventName = "DockPositionChanged";  
            UpdatePanel1.Triggers.Add(saveStateTrigger);  
     
            saveStateTrigger = new AsyncPostBackTrigger();  
            saveStateTrigger.ControlID = dock.ID;  
            saveStateTrigger.EventName = "Command";  
            UpdatePanel1.Triggers.Add(saveStateTrigger);  
        }  
     
        private RadDock CreateRadDockFromState(DockState state)  
        {  
            RadDock dock = new RadDock();  
            dock.DockMode = DockMode.Docked;  
            dock.ID = state.UniqueName;  
            dock.ApplyState(state);  
            dock.Commands.Add(new DockCloseCommand());  
            dock.Commands.Add(new DockExpandCollapseCommand());  
     
            DockCommand dc = new DockCommand();  
            dc.AutoPostBack = true;  
            dc.Name = "Edit";  
            dock.Commands.Add(dc);  
     
            dock.Command += new DockCommandEventHandler(dock_Command);  
            return dock;  
        }  
     
        private DockState CreateDockState(DataLayer.toReadGadgetsRow row)  
        {  
            DockState dockState = new DockState();  
            dockState.UniqueName = row.GadgetId.ToString();  
            dockState.Title = row.Title;  
            dockState.Width = Unit.Pixel(300);  
            DockStateTag tag = new DockStateTag(row.SearchCriteria, row.DisplayRows);  
            dockState.Tag = tag.Tag;  
            dockState.Index = row.Rank;  
            return dockState;  
        }  
     
        private void Initialize()  
        {  
            List<DockState> dockStates = CurrentDockStates;  
            int count = dockStates.Count;  
            for (int i = 0; i < count; i++)  
            {  
                RadDock dock = CreateRadDockFromState(dockStates[i]);  
                //We will just add the RadDock control to the RadDockLayout.  
                // You could use any other control for that purpose, just ensure  
                // that it is inside the RadDockLayout control.  
                // The RadDockLayout control will automatically move the RadDock  
                // controls to their corresponding zone in the LoadDockLayout  
                // event (see below).  
     
                //load gadget control into dock  
                UserControls_Gadget c = (UserControls_Gadget)LoadControl("~/UserControls/Gadget.ascx");  
                c.ID = "Gadget" + i.ToString();  
                DockStateTag tag = new DockStateTag(dock.Tag);  
                c.DisplayRows = tag.DisplayRows;  
                c.SearchCriteria = tag.SearchCriteria;  
     
                dock.ContentContainer.Controls.Add(c);  
     
                rdzGadgets.Controls.Add(dock);  
     
                c.SetTriggers(this.UpdatePanel1);  
     
                //We want to save the dock state every time a dock is moved.  
                CreateSaveStateTrigger(dock);  
     
     
            }  
        }  
     
        protected void Page_Load(object sender, EventArgs e)  
        {  
            //on init, load all docks in this event so display will occur in sequence  
            if (!IsPostBack)  
            {  
                Initialize();  
            }  
        }  
     
        protected void Page_Init(object sender, EventArgs e)  
        {  
            //on postback, initialize dock controls so they will display  
            if (IsPostBack)  
            {  
                Initialize();  
            }  
        }  
     
        void dock_Command(object sender, DockCommandEventArgs e)  
        {  
            if (sender is RadDock)  
            {  
                RadDock radDock = sender as RadDock;  
                switch (e.Command.Name)  
                {  
                    case "Edit":  
                        Response.Redirect(_createPage + radDock.UniqueName);  
                        break;  
                    case "Close":  
                        DataAccess.DeleteGadget(int.Parse(radDock.UniqueName));  
                        break;  
                }  
            }  
        }  
     
        protected void rdlGadgets_LoadDockLayout(object sender, DockLayoutEventArgs e)  
        {  
            //Populate the event args with the state information. The RadDockLayout control  
            // will automatically move the docks according that information.  
            foreach (DockState state in CurrentDockStates)  
            {  
                e.Positions[state.UniqueName] = state.DockZoneID;  
                e.Indices[state.UniqueName] = state.Index;  
            }  
        }  
     
        protected void rdlGadgets_SaveDockLayout(object sender, DockLayoutEventArgs e)  
        {  
            //Save the dock state. This will enable us  
            // to recreate the dock in the next Page_Init.  
            CurrentDockStates = rdlGadgets.GetRegisteredDocksState();  
        }  
     
        protected void btnAdd_Click(object sender, EventArgs e)  
        {  
            Response.Redirect(_createPage + "0");  
        }  
    }  
     


    Source for control
    <%@ Control Language="C#" AutoEventWireup="true" CodeFile="Gadget.ascx.cs" Inherits="UserControls_Gadget" %> 
    <%@ Register TagPrefix="telerik" Namespace="Telerik.Web.UI" Assembly="Telerik.Web.UI" %> 
    <telerik:RadGrid ID="rgGadget" runat="server" Skin="Telerik" ShowHeader="true" AllowPaging="true" 
        ShowStatusBar="false" ShowFooter="False" AllowMultiRowSelection="False" GridLines="none" 
        AutoGenerateColumns="false">  
        <MasterTableView NoMasterRecordsText="No Records Found.">  
            <Columns> 
                <telerik:GridBoundColumn HeaderText="Date Created" DataField="DateCreated" UniqueName="DateCreated" 
                    DataType="System.DateTime" /> 
                <telerik:GridBoundColumn HeaderText="Doc Title" DataField="DocTitle" UniqueName="DocTitle" 
                    DataType="System.String" /> 
                <telerik:GridBoundColumn HeaderText="Doc Name" DataField="DocNme" UniqueName="DocNme" 
                    DataType="System.String" /> 
            </Columns> 
        </MasterTableView> 
        <HeaderStyle Width="250px" /> 
        <ItemStyle Wrap="true" Width="100px" /> 
        <AlternatingItemStyle BackColor="#F0F4F7" /> 
        <ItemStyle BackColor="white" /> 
    </telerik:RadGrid> 
    <asp:Panel ID="pnlNavigation" runat="server">  
        <table width="100%">  
            <tr> 
                <td> 
                    <asp:Button ID="btnFirst" runat="server" Text="<<" OnClick="btnFirst_Click" /></td>  
                <td> 
                    <asp:Button ID="btnPrevious" runat="server" Text="<" OnClick="btnPrevious_Click" /></td>  
                <td> 
                    <asp:Button ID="btnNext" runat="server" Text=">" OnClick="btnNext_Click" /></td>  
                <td> 
                    <asp:Button ID="btnLast" runat="server" Text=">>" OnClick="btnLast_Click" /></td>  
            </tr> 
        </table> 
    </asp:Panel> 

    Code behind for control

    using System;  
    using System.Data;  
    using System.Configuration;  
    using System.Collections;  
    using System.Web;  
    using System.Web.Security;  
    using System.Web.UI;  
    using System.Web.UI.WebControls;  
    using System.Web.UI.WebControls.WebParts;  
    using System.Web.UI.HtmlControls;  
    using Telerik.Web.UI;  
     
    public partial class UserControls_Gadget : System.Web.UI.UserControl  
    {  
        protected void Page_Load(object sender, EventArgs e)  
        {  
        }  
     
        public int DisplayRows  
        {  
            get { return (int)ViewState["DisplayRows"]; }  
            set { ViewState["DisplayRows"] = value; }  
        }  
     
        public string SearchCriteria  
        {  
            set 
            {  
                ViewState["SearchCriteria"] = value;  
                ViewState["PageNumber"] = 0;  
                Bind();  
            }  
        }  
     
        public void SetTriggers(UpdatePanel updatePanel)  
        {  
            RadScriptManager c = Page.Master.FindControl("ScriptManager1"as RadScriptManager;  
            c.RegisterAsyncPostBackControl(this.btnFirst);  
            c.RegisterAsyncPostBackControl(this.btnPrevious);  
            c.RegisterAsyncPostBackControl(this.btnNext);  
            c.RegisterAsyncPostBackControl(this.btnLast);  
     
            //set triggers for all buttons so they can postback  
            //AddButtonClickEventTrigger(updatePanel, this.btnFirst.UniqueID);  
            //AddButtonClickEventTrigger(updatePanel, this.btnPrevious.UniqueID);  
            //AddButtonClickEventTrigger(updatePanel, this.btnNext.UniqueID);  
            //AddButtonClickEventTrigger(updatePanel, this.btnLast.UniqueID);  
        }  
     
        private void Bind()  
        {  
            SearchEngineOutput searchEngine = SearchEngineFactory.GetSearchEngineData(ViewState["SearchCriteria"].ToString());  
            rgGadget.DataSource = searchEngine.Doc;  
            rgGadget.DataBind();  
     
            if (searchEngine.Summary.Rows.Count > 0)  
            {  
                SearchEngineOutput.SummaryRow row = (SearchEngineOutput.SummaryRow)searchEngine.Summary.Rows[0];  
                ViewState["NumFound"] = row.NumFound;  
                if ((int)ViewState["NumFound"] <= (int)ViewState["DisplayRows"])  //no paging necessary  
                {  
                    pnlNavigation.Enabled = false;  
                }  
                else if ((int)ViewState["PageNumber"] == 0) //on first page  
                {  
                    this.btnFirst.Enabled = false;  
                    this.btnPrevious.Enabled = false;  
                    this.btnNext.Enabled = true;  
                    this.btnLast.Enabled = true;  
                }  
                else if (((int)ViewState["PageNumber"] + 1) * (int)ViewState["DisplayRows"] >= (int)ViewState["NumFound"]) //last page  
                {  
                    this.btnFirst.Enabled = true;  
                    this.btnPrevious.Enabled = true;  
                    this.btnNext.Enabled = false;  
                    this.btnLast.Enabled = false;  
                }  
                else 
                {  
                    //in middle  
                    this.btnFirst.Enabled = true;  
                    this.btnPrevious.Enabled = true;  
                    this.btnNext.Enabled = true;  
                    this.btnLast.Enabled = true;  
                }  
            }  
            else 
            {  
                pnlNavigation.Enabled = false;  
            }  
        }  
        protected void btnFirst_Click(object sender, EventArgs e)  
        {  
            ViewState["PageNumber"] = 0;  
            Bind();  
        }  
        protected void btnPrevious_Click(object sender, EventArgs e)  
        {  
            ViewState["PageNumber"] = (int)ViewState["PageNumber"] - 1;  
            Bind();  
        }  
        protected void btnNext_Click(object sender, EventArgs e)  
        {  
            ViewState["PageNumber"] = (int)ViewState["PageNumber"] + 1;  
            Bind();  
        }  
        protected void btnLast_Click(object sender, EventArgs e)  
        {  
            if ((int)ViewState["DisplayRows"] > 0)  
            {  
                int lastPageNumber = (int)ViewState["NumFound"] / (int)ViewState["DisplayRows"];  
                int pageNumberRemainder = (int)ViewState["NumFound"] % (int)ViewState["DisplayRows"];  
                if (pageNumberRemainder > 0)  
                    lastPageNumber++;  
                ViewState["PageNumber"] = lastPageNumber - 1;  
                Bind();  
            }  
        }  
        //public string FirstClientId  
        //{  
        //    get { return this.btnFirst.ClientID; }  
        //}  
        //public string PreviousClientId  
        //{  
        //    get { return this.btnPrevious.ClientID; }  
        //}  
        //public string NextClientId  
        //{  
        //    get { return this.btnNext.ClientID; }  
        //}  
        //public string LastClientId  
        //{  
        //    get { return this.btnLast.ClientID; }  
        //}  
     
        private void AddButtonClickEventTrigger(UpdatePanel updatePanel, string clientId)  
        {  
            AsyncPostBackTrigger clickTrigger = new AsyncPostBackTrigger();  
            clickTrigger.ControlID = clientId;  
            clickTrigger.EventName = "Click";  
            updatePanel.Triggers.Add(clickTrigger);  
        }  
    }  
     
  2. Pero
    Admin
    Pero avatar
    1156 posts

    Posted 28 Jun 2010 Link to this post

    Hi Allan,

    Thank you for the sample project.

    By default when a control, that performs a postback, is placed in an UpdatePanel, you don't need to create an AsyncPostBack trigger as long as the UpdatePanel's ChildrenAsTriggers property is set to true (this is the default value). This being said, I believe the problem comes from the fact that either the UserControl or the RadDock does not have the same ID on every postback. So, please ensure that, whenever you set an ID to a dynamically created control, to set the same ID when the control is recreated.
    For your convenience I reworked your source code into a sample project, and seems to be working without a problem. The project is attached to the thread.

    Sincerely yours,
    Pero
    the Telerik team
    Do you want to have your say when we set our development plans? Do you want to know when a feature you care about is added or when a bug fixed? Explore the Telerik Public Issue Tracking system and vote to affect the priority of the items
  3. UI for ASP.NET Ajax is Ready for VS 2017
  4. Pradeep Enugala
    Pradeep Enugala avatar
    55 posts
    Member since:
    Apr 2010

    Posted 22 Jul 2010 Link to this post

    Hi
       The project zip file does not contain any code except for a web.config file

    Thanks,
    Pradeep.
  5. Pero
    Admin
    Pero avatar
    1156 posts

    Posted 27 Jul 2010 Link to this post

    Hello Pradeep,

    Yes, it seems that I have forgotten to include the source code files. If you need a sample project that shows how to dynamically create RadDock controls and save their state in DB or Session, please take a look at the following samples :


    Regards,
    Pero
    the Telerik team
    Do you want to have your say when we set our development plans? Do you want to know when a feature you care about is added or when a bug fixed? Explore the Telerik Public Issue Tracking system and vote to affect the priority of the items
  6. robertgalvinjr
    robertgalvinjr avatar
    36 posts
    Member since:
    Jun 2006

    Posted 16 Aug 2010 Link to this post

    Hello,

    I was asked to update the application by dynamically loading rad dock controls under dynamically loaded rad tabs.  The application basically works except initially the loaded rad docks in a particular rad zone appear on top of one another.  I'm not sure if this is a symptom but the LoadDockLayout event is never raised.

    The prior version without tabs was working except I had to Initialize the form in the Page_Load event when not posting back and Initialize the form in the Page_Init event when posting back.

    Thanks,

    Al

    ASPX

    <%@ Page Language="C#" AutoEventWireup="true" CodeFile="Default.aspx.cs" Inherits="Default"
        MasterPageFile="~/loggedIn.master" %>
     
    <%@ Register TagPrefix="telerik" Namespace="Telerik.Web.UI" Assembly="Telerik.Web.UI" %>
    <%@ Register Src="~/UserControls/Gadget.ascx" TagName="Gadgets" TagPrefix="uc" %>
    <asp:Content ID="ContentArea" ContentPlaceHolderID="ContentPlaceHolder1" runat="Server">
        <asp:UpdatePanel runat="server" ID="UpdatePanel1">
            <ContentTemplate>
                <telerik:RadTabStrip ID="rtsDockTabs" runat="server" MultiPageID="rmpDockTab"/>
                <telerik:RadMultiPage ID="rmpDockTab" runat="server" SelectedIndex="0"/>
            </ContentTemplate>
        </asp:UpdatePanel>
        <br />
        <asp:Button ID="btnAdd" runat="server" Text="Add" OnClick="btnAdd_Click" />
    </asp:Content>

    CS

    using System;
    using System.Data;
    using System.Configuration;
    using System.Collections;
    using System.Web;
    using System.Web.Security;
    using System.Web.UI;
    using System.Web.UI.WebControls;
    using System.Web.UI.WebControls.WebParts;
    using System.Web.UI.HtmlControls;
    using Telerik.Web.UI;
    using System.Collections.Generic;
     
    public partial class Default : System.Web.UI.Page
    {
        private const string _createPage = "CreateGadget.aspx?Id=";
     
        private List<DockState> CurrentDockStates
        {
            get
            {
                //Store the info about the added docks in the session. For real life
                // applications we recommend using database or other storage medium
                // for persisting this information.
                //get data
                DataLayer.toReadGadgetsDataTable gadgets = DataAccess.GetGadgets(Users.UserInfo.UserId);
     
                List<DockState> currentDockStates = new List<DockState>();
     
                foreach (DataRow dr in gadgets.Rows)
                {
                    DataLayer.toReadGadgetsRow row = dr as DataLayer.toReadGadgetsRow;
     
                    currentDockStates.Add(CreateDockState(row));
                }
     
                return currentDockStates;
            }
            set
            {
                List<DockState> currentDockStates = value;
     
                foreach (DockState dockState in currentDockStates)
                {
                    DockStateTag tag = new DockStateTag(dockState.Tag);
                    //update gadget in db
                    DataAccess.UpdateGadget(
                        int.Parse(dockState.UniqueName),
                        tag.SearchCriteria,
                        dockState.Title,
                        dockState.Index,
                        tag.DisplayRows
                        );
                }
            }
        }
     
        private void CreateSaveStateTrigger(RadDock dock)
        {
            //Ensure that the RadDock control will initiate postback
            // when its position changes on the client or any of the commands is clicked.
            //Using the trigger we will "ajaxify" that postback.
            dock.AutoPostBack = true;
            dock.CommandsAutoPostBack = true;
     
            AsyncPostBackTrigger saveStateTrigger = new AsyncPostBackTrigger();
            saveStateTrigger.ControlID = dock.ID;
            saveStateTrigger.EventName = "DockPositionChanged";
            UpdatePanel1.Triggers.Add(saveStateTrigger);
     
            saveStateTrigger = new AsyncPostBackTrigger();
            saveStateTrigger.ControlID = dock.ID;
            saveStateTrigger.EventName = "Command";
            UpdatePanel1.Triggers.Add(saveStateTrigger);
        }
     
        private RadDock CreateRadDockFromState(DockState state)
        {
            RadDock dock = new RadDock();
            dock.DockMode = DockMode.Docked;
            dock.ID = state.UniqueName;
            dock.ApplyState(state);
            dock.Commands.Add(new DockCloseCommand());
            dock.Commands.Add(new DockExpandCollapseCommand());
     
            DockCommand dc = new DockCommand();
            dc.AutoPostBack = true;
            dc.Name = "Edit";
            dc.Text = "Edit";
            dock.Commands.Add(dc);
     
            dock.Command += new DockCommandEventHandler(dock_Command);
            return dock;
        }
     
        private DockState CreateDockState(DataLayer.toReadGadgetsRow row)
        {
            DockState dockState = new DockState();
            dockState.UniqueName = row.GadgetId.ToString();
            dockState.Title = row.Title;
            dockState.Width = Unit.Pixel(300);
            DockStateTag tag = new DockStateTag(row.SearchCriteria, row.DisplayRows, row.TabId, row.TabName);
            dockState.Tag = tag.Tag;
            dockState.Index = row.Rank;
            return dockState;
        }
     
        private void Initialize()
        {
            //add all tabs
            DataLayer.toReadTabsDataTable readTabsDataTable = DataAccess.GetTabs(Users.UserInfo.UserId);
            foreach (DataRow dr in readTabsDataTable.Rows)
            {
                DataLayer.toReadTabsRow row = (DataLayer.toReadTabsRow)dr;
                AddTab(row.Name, row.TabId);
                AddPageView(row.Name);
                CreateLayout(rmpDockTab.FindPageViewByID(row.Name));
            }
        }
     
        private void CreateLayout(RadPageView pageView)
        {
            //add raddocklayout
            RadDockLayout dockLayout = new RadDockLayout();
            dockLayout.ID = "rdlGadgets_" + pageView.ID;
            dockLayout.LoadDockLayout += new DockLayoutEventHandler(rdlGadgets_SaveDockLayout);
            dockLayout.SaveDockLayout += new DockLayoutEventHandler(rdlGadgets_SaveDockLayout);
     
            //add dock zone
            RadDockZone dockZone = new RadDockZone();
            dockZone.ID = "rdzGadgets_" + pageView.ID;
            dockZone.Orientation = Orientation.Horizontal;
            dockZone.Width = new Unit(100.0, UnitType.Percentage);
            dockZone.MinHeight =  new Unit(200);
     
            dockZone.Style["float"] = "left";
            dockZone.Style["margin-right"] = "20px";
     
            List<DockState> dockStates = CurrentDockStates;
            int count = dockStates.Count;
            for (int i = 0; i < count; i++)
            {
                RadDock dock = CreateRadDockFromState(dockStates[i]);
     
                DockStateTag tag = new DockStateTag(dock.Tag);
     
                //check which controls belong to this tab
                if (tag.TabName == pageView.ID)
                {
                    //We will just add the RadDock control to the RadDockLayout.
                    // You could use any other control for that purpose, just ensure
                    // that it is inside the RadDockLayout control.
                    // The RadDockLayout control will automatically move the RadDock
                    // controls to their corresponding zone in the LoadDockLayout
                    // event (see below).
     
                    //load gadget control into dock
                    UserControls_Gadget c = (UserControls_Gadget)LoadControl("~/UserControls/Gadget.ascx");
                    c.ID = tag.TabName + "_Gadget" + i.ToString();
                    c.DisplayRows = tag.DisplayRows;
                    c.SearchCriteria = tag.SearchCriteria;
     
                    dock.ContentContainer.Controls.Add(c);
     
                    //add to doc zone
                    dockZone.Controls.Add(dock);
     
                    //We want to save the dock state every time a dock is moved.
                    CreateSaveStateTrigger(dock);
                }
            }
     
            //add to layout
            dockLayout.Controls.Add(dockZone);
     
            //add to pageview
            pageView.Controls.Add(dockLayout);
        }
     
        private void AddTab(string tabName, int tabValue)
        {
            RadTab tab = new RadTab();
            tab.Text = tabName;
            tab.PageViewID = tabName;
            //tab.ID = "Tab_" + tabName;
            tab.Value = tabValue.ToString();
            rtsDockTabs.Tabs.Add(tab);
        }
     
        private void AddPageView(string id)
        {
            RadPageView pageView = new RadPageView();
            pageView.ID = id;
            rmpDockTab.PageViews.Add(pageView);
        }
     
        protected void Page_Load(object sender, EventArgs e)
        {
            //on init, load all docks in this event so display will occur in sequence
            if (!IsPostBack)
            {
                //Initialize();
            }
        }
     
        protected void Page_Init(object sender, EventArgs e)
        {
            //on postback, initialize dock controls so they will display
            //if (IsPostBack)
            {
                Initialize();
            }
        }
     
        void dock_Command(object sender, DockCommandEventArgs e)
        {
            if (sender is RadDock)
            {
                RadDock radDock = sender as RadDock;
                switch (e.Command.Name)
                {
                    case "Edit":
                        Response.Redirect(_createPage + radDock.UniqueName);
                        break;
                    case "Close":
                        DataAccess.DeleteGadget(int.Parse(radDock.UniqueName));
                        break;
                }
            }
        }
     
        protected void rdlGadgets_LoadDockLayout(object sender, DockLayoutEventArgs e)
        {
            //Populate the event args with the state information. The RadDockLayout control
            // will automatically move the docks according that information.
            foreach (DockState state in CurrentDockStates)
            {
                e.Positions[state.UniqueName] = state.DockZoneID;
                e.Indices[state.UniqueName] = state.Index;
            }
        }
     
        protected void rdlGadgets_SaveDockLayout(object sender, DockLayoutEventArgs e)
        {
            //Save the dock state. This will enable us
            // to recreate the dock in the next Page_Init.
            CurrentDockStates = ((RadDockLayout)sender).GetRegisteredDocksState();
        }
     
        protected void btnAdd_Click(object sender, EventArgs e)
        {
            Response.Redirect(_createPage + "0");
        }
    }
  7. Pero
    Admin
    Pero avatar
    1156 posts

    Posted 19 Aug 2010 Link to this post

    Hi Al,

    The reason why the LoadDockLayout event handler method (i.e. rdlGadgets_LoadDockLayout) is never executed, is the fact that both RadDockLayout events have exactly the same handler, as shown in the following part from your code:

    private void CreateLayout(RadPageView pageView)
    {
            //add raddocklayout
            RadDockLayout dockLayout = new RadDockLayout();
            dockLayout.ID = "rdlGadgets_" + pageView.ID;
            dockLayout.LoadDockLayout += new DockLayoutEventHandler(rdlGadgets_SaveDockLayout);
            dockLayout.SaveDockLayout += new DockLayoutEventHandler(rdlGadgets_SaveDockLayout);

    After modifying the code to attach the correct handler method everything seems to be working fine:

    dockLayout.LoadDockLayout += new DockLayoutEventHandler(rdlGadgets_LoadDockLayout);
    dockLayout.SaveDockLayout += new DockLayoutEventHandler(rdlGadgets_SaveDockLayout);

    Regards,
    Pero
    the Telerik team
    Do you want to have your say when we set our development plans? Do you want to know when a feature you care about is added or when a bug fixed? Explore the Telerik Public Issue Tracking system and vote to affect the priority of the items
  8. Allan
    Allan avatar
    10 posts
    Member since:
    Jun 2009

    Posted 19 Aug 2010 Link to this post

    Thanks, Pero.  Good catch.  The load event is now firing but the original issue remains.  The raddocks initially load on top of one another.

    THank again,

    Al
  9. Allan
    Allan avatar
    10 posts
    Member since:
    Jun 2009

    Posted 23 Aug 2010 Link to this post

    Pero,

    I also noticed that the add button is not initially displayed on the web form.

    Thanks,

    Al
  10. Pero
    Admin
    Pero avatar
    1156 posts

    Posted 24 Aug 2010 Link to this post

    Hi Al,

    I was not able to run the code as is, so I was not able to reproduce the problem locally. Could you please provide fully runnable project, that will help us reproduce the issue locally? I have attached the modified source code that I tested.

    On a side note, is the application working correctly with non master page scenario, i.e. in a standard ASP.NET page? The DockZoneID property of the RadDock and the DockState, should contain the ClientID of the RadDockZone, to which the dock is docked. In master page scenario, the ClientID of the docking zones are different than the server ones. In case you have predefined dock states in the DataBase, please make sure the DockZoneID's are the correct ones.

    Kind regards,
    Pero
    the Telerik team
    Do you want to have your say when we set our development plans? Do you want to know when a feature you care about is added or when a bug fixed? Explore the Telerik Public Issue Tracking system and vote to affect the priority of the items
  11. Allan
    Allan avatar
    10 posts
    Member since:
    Jun 2009

    Posted 24 Aug 2010 Link to this post

    Pero,

    I would like to attach my solution, but how can I do it?  Otherwise, what files do you need?

    Thanks,

    Al
  12. Allan
    Allan avatar
    10 posts
    Member since:
    Jun 2009

    Posted 24 Aug 2010 Link to this post

    Pero,

    I am attaching the master page and the dockstatetag helper class to help with your build.

    Upon further review, I have more diagnostic information.  When creating the layout:

    1) Everything seems to be fine until the docklayout is added to the pageview.  pageView.Controls.Add(dockLayout)
    2) In the debugger, if I try to examine a property of a raddock by using the Docks property (i.e. ((RadDockZone)(pageView.Controls[0].Controls[0])).Docks[0].ID), I get an error '((RadDockZone)(pageView.Controls[0].Controls[0])).Docks[0]' threw an exception of type 'System.ArgumentOutOfRangeException'
    3) If I examine ((RadDockZone)(pageView.Controls[0].Controls[0])).Controls[0], the type is a raddock, but the DockZoneId propery is "".
    4) When the dockzone is added to the docklayout, everything is fine.

    I also noticed that you are loading the raddoczone twice on the first load.  I am not doing that.  Why is this necessary? 

    Also, I do not have separate CreateRadDock and CreateRadDockFromState methods which do close to the same thing.    Why is this necessary?

    Lastly, the uniquename and id of your RadDock is much different and longer than mine.  Is this an issue?

    Thanks,

    Al

    DockStateTag.cs

    using System;
    using System.Data;
    using System.Configuration;
    using System.Web;
    using System.Web.Security;
    using System.Web.UI;
    using System.Web.UI.WebControls;
    using System.Web.UI.WebControls.WebParts;
    using System.Web.UI.HtmlControls;
     
    /// <summary>
    /// Summary description for DockStateTag
    /// </summary>
    public class DockStateTag
    {
        string _tag;
        private const string _tagDelimiter = "|";
         
        public DockStateTag(string searchCriteria, int displayRows, int tabId, string tabName)
        {
            _tag =
                searchCriteria
                + _tagDelimiter + displayRows.ToString()
                + _tagDelimiter + tabId.ToString()
                + _tagDelimiter + tabName;
        }
     
        public DockStateTag(string tag)
        {
            _tag = tag;
        }
     
        public string Tag
        {
            get { return _tag; }
        }
     
        private string[] Split()
        {
            return Tag.Split(new string[] { _tagDelimiter }, StringSplitOptions.None);
        }
     
        public string SearchCriteria
        {
            get
            {
                return Split()[0];
            }
        }
     
        public int DisplayRows
        {
            get
            {
                return int.Parse(Split()[1]);
            }
        }
     
        public int TabId
        {
            get
            {
                return int.Parse(Split()[2]);
            }
        }
     
        public string TabName
        {
            get
            {
                return Split()[3];
            }
        }
    }

    Loggedin.master

    <%@ Master Language="C#" AutoEventWireup="true" CodeFile="loggedin.master.cs" Inherits="loggedin" %>
    <%@ Register TagPrefix="telerik" Namespace="Telerik.Web.UI" Assembly="Telerik.Web.UI" %>
    <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
    <head runat="server">
        <title>IGoogle</title>
        <link href="Style/PageStyle.css" type="text/css" rel="STYLESHEET" />
    </head>
    <body topmargin="0" leftmargin="0" rightmargin="0" bottommargin="0">
        <form id="form1" runat="server">
            <asp:ScriptManager ID="ScriptManager1" runat="server" />
            <table border="0" cellpadding="0" cellspacing="0" width="100%">
                <tr>
                    <td>
                        <table width="100%" cellpadding="10" cellspacing="0" border="0">
                            <tr>
                                <td>
                                    <asp:Image ID="Image1" runat="server" ImageUrl="~/images/symbol_logo_sm_Moto.jpg" /></td>
                            </tr>
                        </table>
                    </td>
                </tr>
                <tr>
                    <td colspan="2" id="title">
                        <table class="header_table" border="0">
                            <tr>
                                <td>
                                    <h1>
                                         Welcome to IGoogle
                                    </h1>
                                </td>
                                <td align="right">
                                    <table>
                                        <tr>
                                            <td align="right">
                                                <b>Welcome <asp:Label ID="FullUserName" runat="server"></asp:Label></b>  </td>
                                        </tr>
                                    </table>
                                </td>
                            </tr>
                            <tr><td>
                        <br />
                        <asp:LinkButton ID="lbAdmin" runat="server" Text="Admin" PostBackUrl="~/Admin.aspx" />
                            </td></tr>
                        </table>
                    </td>
                </tr>
                <tr>
                    <td valign="top">
                        <table width="100%" border="0" cellpadding="0" cellspacing="0">
                            <tr>
                                <td>
                                     </td>
                            </tr>
                            <tr>
                                <td>
                                    <asp:ContentPlaceHolder ID="ContentPlaceHolder1" runat="server">
                                    </asp:ContentPlaceHolder>
                                </td>
                            </tr>
                        </table>
                    </td>
                </tr>
            </table>
        </form>
    </body>
    </html>

    loggedin.master.cs

    using System;
    using System.Data;
    using System.Configuration;
    using System.Collections;
    using System.Web;
    using System.Web.Security;
    using System.Web.UI;
    using System.Web.UI.WebControls;
    using System.Web.UI.WebControls.WebParts;
    using System.Web.UI.HtmlControls;
    using Telerik.Web.UI;
     
    /// <summary>
    /// master page used after log in
    /// </summary>
    public partial class loggedin : System.Web.UI.MasterPage
    {
        /// <summary>
        /// Page load event
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        protected void Page_Load(object sender, EventArgs e)
        {
            if (!IsPostBack)
            {
                //load dynamic menu
                Users u = (Users)Session["Users"];
                FullUserName.Text = Users.UserInfo.FullName;
     
                //check if admin
                this.lbAdmin.Visible = u.GetRoles.Contains("Admin");
            }
        }
    }
  13. Pero
    Admin
    Pero avatar
    1156 posts

    Posted 26 Aug 2010 Link to this post

    Hi Allan,

    Thank you for the additional source code, I was not able to run it, but after careful examination I think I know what's causing the issue.

    The reason why the docks are stacked one on top the other, when the page is loaded for the first time is because the DockState that gets applied to the dock, does not have DockZoneID property specified, i.e. DockState.DockZoneID=string.Empty;. This is the code that creates the DockStates:

    private List<DockState> CurrentDockStates
    {
        get
        {
            //Store the info about the added docks in the session. For real life
            // applications we recommend using database or other storage medium
            // for persisting this information.
            //get data
            DataLayer.toReadGadgetsDataTable gadgets = DataAccess.GetGadgets(Users.UserInfo.UserId);
     
            List<DockState> currentDockStates = new List<DockState>();
     
            foreach (DataRow dr in gadgets.Rows)
            {
                DataLayer.toReadGadgetsRow row = dr as DataLayer.toReadGadgetsRow;
     
                currentDockStates.Add(CreateDockState(row));
            }
     
            return currentDockStates;
        }
        set
        {
            List<DockState> currentDockStates = value;
     
            foreach (DockState dockState in currentDockStates)
            {
                DockStateTag tag = new DockStateTag(dockState.Tag);
                //update gadget in db
                DataAccess.UpdateGadget(
                    int.Parse(dockState.UniqueName),
                    tag.SearchCriteria,
                    dockState.Title,
                    dockState.Index,
                    tag.DisplayRows
                    );
            }
        }
    }
     
     
    private DockState CreateDockState(DataLayer.toReadGadgetsRow row)
    {
        DockState dockState = new DockState();
        dockState.UniqueName = row.GadgetId.ToString();
        dockState.Title = row.Title;
        dockState.Width = Unit.Pixel(300);
        DockStateTag tag = new DockStateTag(row.SearchCriteria, row.DisplayRows, row.TabId, row.TabName);
        dockState.Tag = tag.Tag;
        dockState.Index = row.Rank;
        return dockState;
    }

    As you can see the DockZoneID is never set.
    The CurrentDockStates property is later used in the LoadDockLayout event handler to set the dock's zone and position in the zone, so the DockLayout can reposition the docks in their correct places:
    protected void rdlGadgets_LoadDockLayout(object sender, DockLayoutEventArgs e)
    {
        //Populate the event args with the state information. The RadDockLayout control
        // will automatically move the docks according that information.
        foreach (DockState state in CurrentDockStates)
        {
            e.Positions[state.UniqueName] = state.DockZoneID;
            e.Indices[state.UniqueName] = state.Index;
        }
    }
    Basically in this method we set empty DockZoneID to every dock, which means we make the docks floating, and that's why they stack one on top the other. To demonstrate that this is happening I created a sample page that creates a single dock, and then in the LoadDockLayout event I set the DockZoneID to an empty string. The sample project is attached to the thread.

    To avoid this issue you need to set the DockZoneID property of the DockState to the ClientID of the docking zone where the dock should be placed. I suppose this can be done in the CreateLayout method, just before you create the dock from state. One thing you should take into consideration is to add the DockLayout and the DockZone to the page, before the docks are added to the page, to make sure the correct ClientID of the zone is set to the DockState. The code should be similar to the following:
    private void CreateLayout(RadPageView pageView)
    {
        //add raddocklayout
        RadDockLayout dockLayout = new RadDockLayout();
        dockLayout.ID = "rdlGadgets_" + pageView.ID;
        dockLayout.LoadDockLayout += new DockLayoutEventHandler(rdlGadgets_LoadDockLayout);
        dockLayout.SaveDockLayout += new DockLayoutEventHandler(rdlGadgets_SaveDockLayout);
     
        //add dock zone
        RadDockZone dockZone = new RadDockZone();
        dockZone.ID = "rdzGadgets_" + pageView.ID;
        dockZone.Orientation = Orientation.Horizontal;
        dockZone.Width = new Unit(100.0, UnitType.Percentage);
        dockZone.MinHeight = new Unit(200);
     
        dockZone.Style["float"] = "left";
        dockZone.Style["margin-right"] = "20px";
                
                 //add to layout
                 dockLayout.Controls.Add(dockZone);

                 //add to pageview
                 pageView.Controls.Add(dockLayout);

        List<DockState> dockStates = CurrentDockStates;
        int count = dockStates.Count;
        for (int i = 0; i < count; i++)
        {
               dockStates[i].DockZoneID = dockZone.ClientID;
            RadDock dock = CreateRadDockFromState(dockStates[i]);
     
            DockStateTag tag = new DockStateTag(dock.Tag);
     
            //check which controls belong to this tab
            if (tag.TabName == pageView.ID)
            {
                //We will just add the RadDock control to the RadDockLayout.
                // You could use any other control for that purpose, just ensure
                // that it is inside the RadDockLayout control.
                // The RadDockLayout control will automatically move the RadDock
                // controls to their corresponding zone in the LoadDockLayout
                // event (see below).
     
                //load gadget control into dock
                UserControls_Gadget c = (UserControls_Gadget)LoadControl("~/UserControls/Gadget.ascx");
                c.ID = tag.TabName + "_Gadget" + i.ToString();
                c.DisplayRows = tag.DisplayRows;
                c.SearchCriteria = tag.SearchCriteria;
     
                dock.ContentContainer.Controls.Add(c);
     
                //add to doc zone
                dockZone.Controls.Add(dock);
     
                //We want to save the dock state every time a dock is moved.
                CreateSaveStateTrigger(dock);
            }
        }   
    }


    Regarding your questions:
    • Everything is OK when the dock zone is added to the docklayout because, until that moment the zone is not present in the Controls collection, and that's why an exception is thrown when you try to access the dock.
    • Could you please let me know in which code file I am loading the dock zone twice? I couldn't find that source code. It is enough to load the dock zone once, if you are adding only a single zone. More than one zone with the same ID will cause an exception.
    • When we implemented the sample, we created to methods for creating docks. This makes the code more readable, because you know whether the dock is created from state (i.e. an existing dock) or a new one. This is not necessary. You can unite this methods, or implement a new one, that will suit your specific scenario.
    • The length of the UniqueName and the server ID of the dock is not an issue. As long as the ID starts with an alphabetic character (i.e. with a letter), and does not contain "-" characters the length is not an issue.

    I hope this helps.

    Regards,
    Pero
    the Telerik team
    Do you want to have your say when we set our development plans? Do you want to know when a feature you care about is added or when a bug fixed? Explore the Telerik Public Issue Tracking system and vote to affect the priority of the items
  14. Allan
    Allan avatar
    10 posts
    Member since:
    Jun 2009

    Posted 26 Aug 2010 Link to this post

    Pero,

    I made the specified changes, but the raddocks still appear on top of one another.

    Is there anything I can do to help duplicate the error?

    Thanks,

    Al

    P.S. I am also attaching your code that will load the radzone twice on !ISPostback.

    P.P.S. I am experiencing the same behavior without a master page


    My Code with the specified changes

    private void CreateLayout(RadPageView pageView)
    {
        //add raddocklayout
        RadDockLayout dockLayout = new RadDockLayout();
        dockLayout.ID = "rdlGadgets_" + pageView.ID;
        dockLayout.LoadDockLayout += new DockLayoutEventHandler(rdlGadgets_LoadDockLayout);
        dockLayout.SaveDockLayout += new DockLayoutEventHandler(rdlGadgets_SaveDockLayout);
        //add dock zone
        RadDockZone dockZone = new RadDockZone();
        dockZone.ID = "rdzGadgets_" + pageView.ID;
        dockZone.Orientation = Orientation.Horizontal;
        dockZone.Width = new Unit(100.0, UnitType.Percentage);
        dockZone.MinHeight =  new Unit(200);
        dockZone.Style["float"] = "left";
        dockZone.Style["margin-right"] = "20px";
        //add to layout
        dockLayout.Controls.Add(dockZone);
        //add to pageview
        pageView.Controls.Add(dockLayout);
        List<DockState> dockStates = CurrentDockStates;
        int count = dockStates.Count;
        for (int i = 0; i < count; i++)
        {
            dockStates[i].DockZoneID = dockZone.ClientID;
            RadDock dock = CreateRadDockFromState(dockStates[i]);
            DockStateTag tag = new DockStateTag(dock.Tag);
            //check which controls belong to this tab
            if (tag.TabName == pageView.ID)
            {
                //We will just add the RadDock control to the RadDockLayout.
                // You could use any other control for that purpose, just ensure
                // that it is inside the RadDockLayout control.
                // The RadDockLayout control will automatically move the RadDock
                // controls to their corresponding zone in the LoadDockLayout
                // event (see below).
                //load gadget control into dock
                UserControls_Gadget c = (UserControls_Gadget)LoadControl("~/UserControls/Gadget.ascx");
                c.ID = tag.TabName + "_Gadget" + i.ToString();
                c.DisplayRows = tag.DisplayRows;
                c.SearchCriteria = tag.SearchCriteria;
                dock.ContentContainer.Controls.Add(c);
                //add to doc zone
                dockZone.Controls.Add(dock);
                //We want to save the dock state every time a dock is moved.
                CreateSaveStateTrigger(dock);
            }
        }
    }

    Your code that loads raddoczone twice:

    private void CreateLayout(RadPageView pageView)
    {
        //add raddocklayout
        RadDockLayout dockLayout = new RadDockLayout();
        dockLayout.ID = "rdlGadgets_" + pageView.ID;
        dockLayout.LoadDockLayout += new DockLayoutEventHandler(rdlGadgets_LoadDockLayout);
        dockLayout.SaveDockLayout += new DockLayoutEventHandler(rdlGadgets_SaveDockLayout);
        //add dock zone
        RadDockZone dockZone = new RadDockZone();
        dockZone.ID = "rdzGadgets_" + pageView.ID;
        dockZone.Orientation = Orientation.Horizontal;
        dockZone.Width = new Unit(100.0, UnitType.Percentage);
        dockZone.MinHeight = new Unit(200);
        dockZone.Style["float"] = "left";
        dockZone.Style["margin-right"] = "20px";
        if (!IsPostBack)
        {
            for (int i = 0; i < 3; i++)
            {
                RadDock dock = CreateRadDock();
                Control c = LoadControl("~/UserControls/Weather.ascx");
                c.ID = "Widget" + dock.UniqueName;
                dock.ContentContainer.Controls.Add(c);
                //add to doc zone
                dockZone.Controls.Add(dock);
                //We want to save the dock state every time a dock is moved.
                CreateSaveStateTrigger(dock);
            }
        }
        List<DockState> dockStates = CurrentDockStates;
        int count = dockStates.Count;
        for (int i = 0; i < count; i++)
        {
            RadDock dock = CreateRadDockFromState(dockStates[i]);
            Control c = LoadControl("~/UserControls/Weather.ascx");
            c.ID = "Widget" + dock.UniqueName;
            dock.ContentContainer.Controls.Add(c);
            //add to doc zone
            dockZone.Controls.Add(dock);
            //We want to save the dock state every time a dock is moved.
            CreateSaveStateTrigger(dock);
        }
        //add to layout
        dockLayout.Controls.Add(dockZone);
        //add to pageview
        pageView.Controls.Add(dockLayout);
    }


  15. Allan
    Allan avatar
    10 posts
    Member since:
    Jun 2009

    Posted 26 Aug 2010 Link to this post

    Pero,

    To help reproduce the problem, I scaled down the project and removed the dependency of the database.  When I run this project, I get two raddocks on top of one another.

    Thanks,

    Al

    App_Code folder

    DataAccess.cs

    using System;
    using System.Data;
    using System.Configuration;
    using System.Web;
    using System.Web.Security;
    using System.Web.UI;
    using System.Web.UI.WebControls;
    using System.Web.UI.WebControls.WebParts;
    using System.Web.UI.HtmlControls;
      
    /// <summary>
    /// Summary description for DataAccess
    /// </summary>
    public static class DataAccess
    {
        public static DataLayer.toReadGadgetsDataTable GetGadgets(int userId)
        {
            DataLayer.toReadGadgetsDataTable table = new DataLayer.toReadGadgetsDataTable();
            table.AddtoReadGadgetsRow("Search1", 0, "Title1", 5, 1, "Tab1");
            table.AddtoReadGadgetsRow("Search2", 1, "Title2", 5, 1, "Tab1");
            table.AddtoReadGadgetsRow("Search3", 0, "Title3", 5, 2, "Tab2");
            table.AddtoReadGadgetsRow("Search4", 1, "Title4", 5, 2, "Tab2");
            return table;
        }
      
        public static DataLayer.toReadTabsDataTable GetTabs(int userId)
        {
            DataLayer.toReadTabsDataTable table = new DataLayer.toReadTabsDataTable();
            table.AddtoReadTabsRow("Tab1");
            table.AddtoReadTabsRow("Tab2");
            return table;
        }
    }

    DataLayer.xsd

    <?xml version="1.0" encoding="utf-8"?>
    <xs:schema id="DataLayer" targetNamespace="http://tempuri.org/DataLayer.xsd" xmlns:mstns="http://tempuri.org/DataLayer.xsd" xmlns="http://tempuri.org/DataLayer.xsd" xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata" xmlns:msprop="urn:schemas-microsoft-com:xml-msprop" attributeFormDefault="qualified" elementFormDefault="qualified">
      <xs:annotation>
        <xs:appinfo source="urn:schemas-microsoft-com:xml-msdatasource">
          <DataSource DefaultConnectionIndex="0" FunctionsComponentName="QueriesTableAdapter" Modifier="AutoLayout, AnsiClass, Class, Public" SchemaSerializationMode="IncludeSchema" xmlns="urn:schemas-microsoft-com:xml-msdatasource">
            <Connections>
              <Connection AppSettingsObjectName="Web.config" AppSettingsPropertyName="ConnectionString" ConnectionStringObject="" IsAppSettingsProperty="True" Modifier="Assembly" Name="ConnectionString (Web.config)" ParameterPrefix="@" PropertyReference="AppConfig.System.Configuration.ConfigurationManager.0.ConnectionStrings.ConnectionString.ConnectionString" Provider="System.Data.SqlClient">
              </Connection>
            </Connections>
            <Tables>
              <TableAdapter BaseClass="System.ComponentModel.Component" DataAccessorModifier="AutoLayout, AnsiClass, Class, Public" DataAccessorName="toReadTabsTableAdapter" GeneratorDataComponentClassName="toReadTabsTableAdapter" Name="toReadTabs" UserDataComponentName="toReadTabsTableAdapter">
                <MainSource>
                  <DbSource ConnectionRef="ConnectionString (Web.config)" DbObjectName="IGoogle.dbo.toReadTabs" DbObjectType="StoredProcedure" GenerateMethods="Get" GenerateShortCommands="False" GeneratorGetMethodName="GetData" GetMethodModifier="Public" GetMethodName="GetData" QueryType="Rowset" ScalarCallRetval="System.Object, mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" UseOptimisticConcurrency="False" UserGetMethodName="GetData" UserSourceName="GetData">
                    <SelectCommand>
                      <DbCommand CommandType="StoredProcedure" ModifiedByUser="False">
                        <CommandText>dbo.toReadTabs</CommandText>
                        <Parameters>
                          <Parameter AllowDbNull="True" AutogeneratedName="" DataSourceName="" DbType="Int32" Direction="ReturnValue" ParameterName="@RETURN_VALUE" Precision="10" ProviderType="Int" Scale="0" Size="4" SourceColumnNullMapping="False" SourceVersion="Current">
                          </Parameter>
                          <Parameter AllowDbNull="True" AutogeneratedName="" DataSourceName="" DbType="Int32" Direction="Input" ParameterName="@UserId" Precision="10" ProviderType="Int" Scale="0" Size="4" SourceColumnNullMapping="False" SourceVersion="Current">
                          </Parameter>
                        </Parameters>
                      </DbCommand>
                    </SelectCommand>
                  </DbSource>
                </MainSource>
                <Mappings>
                  <Mapping SourceColumn="TabId" DataSetColumn="TabId" />
                  <Mapping SourceColumn="Name" DataSetColumn="Name" />
                </Mappings>
                <Sources>
                </Sources>
              </TableAdapter>
              <TableAdapter BaseClass="System.ComponentModel.Component" DataAccessorModifier="AutoLayout, AnsiClass, Class, Public" DataAccessorName="toReadGadgetsTableAdapter" GeneratorDataComponentClassName="toReadGadgetsTableAdapter" Name="toReadGadgets" UserDataComponentName="toReadGadgetsTableAdapter">
                <MainSource>
                  <DbSource ConnectionRef="ConnectionString (Web.config)" DbObjectName="IGoogle.dbo.toReadGadgets" DbObjectType="StoredProcedure" GenerateMethods="Get" GenerateShortCommands="False" GeneratorGetMethodName="GetData" GetMethodModifier="Public" GetMethodName="GetData" QueryType="Rowset" ScalarCallRetval="System.Object, mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" UseOptimisticConcurrency="False" UserGetMethodName="GetData" UserSourceName="GetData">
                    <SelectCommand>
                      <DbCommand CommandType="StoredProcedure" ModifiedByUser="False">
                        <CommandText>dbo.toReadGadgets</CommandText>
                        <Parameters>
                          <Parameter AllowDbNull="True" AutogeneratedName="" DataSourceName="" DbType="Int32" Direction="ReturnValue" ParameterName="@RETURN_VALUE" Precision="10" ProviderType="Int" Scale="0" Size="4" SourceColumnNullMapping="False" SourceVersion="Current">
                          </Parameter>
                          <Parameter AllowDbNull="True" AutogeneratedName="" DataSourceName="" DbType="Int32" Direction="Input" ParameterName="@UserId" Precision="10" ProviderType="Int" Scale="0" Size="4" SourceColumnNullMapping="False" SourceVersion="Current">
                          </Parameter>
                        </Parameters>
                      </DbCommand>
                    </SelectCommand>
                  </DbSource>
                </MainSource>
                <Mappings>
                  <Mapping SourceColumn="GadgetId" DataSetColumn="GadgetId" />
                  <Mapping SourceColumn="SearchCriteria" DataSetColumn="SearchCriteria" />
                  <Mapping SourceColumn="Rank" DataSetColumn="Rank" />
                  <Mapping SourceColumn="Title" DataSetColumn="Title" />
                  <Mapping SourceColumn="DisplayRows" DataSetColumn="DisplayRows" />
                  <Mapping SourceColumn="TabId" DataSetColumn="TabId" />
                  <Mapping SourceColumn="TabName" DataSetColumn="TabName" />
                </Mappings>
                <Sources>
                </Sources>
              </TableAdapter>
            </Tables>
            <Sources>
            </Sources>
          </DataSource>
        </xs:appinfo>
      </xs:annotation>
      <xs:element name="DataLayer" msdata:IsDataSet="true" msdata:UseCurrentLocale="true" msprop:Generator_UserDSName="DataLayer" msprop:Generator_DataSetName="DataLayer">
        <xs:complexType>
          <xs:choice minOccurs="0" maxOccurs="unbounded">
            <xs:element name="toReadTabs" msprop:Generator_UserTableName="toReadTabs" msprop:Generator_RowDeletedName="toReadTabsRowDeleted" msprop:Generator_RowChangedName="toReadTabsRowChanged" msprop:Generator_RowClassName="toReadTabsRow" msprop:Generator_RowChangingName="toReadTabsRowChanging" msprop:Generator_RowEvArgName="toReadTabsRowChangeEvent" msprop:Generator_RowEvHandlerName="toReadTabsRowChangeEventHandler" msprop:Generator_TableClassName="toReadTabsDataTable" msprop:Generator_TableVarName="tabletoReadTabs" msprop:Generator_RowDeletingName="toReadTabsRowDeleting" msprop:Generator_TablePropName="toReadTabs">
              <xs:complexType>
                <xs:sequence>
                  <xs:element name="TabId" msdata:ReadOnly="true" msdata:AutoIncrement="true" msprop:Generator_UserColumnName="TabId" msprop:Generator_ColumnVarNameInTable="columnTabId" msprop:Generator_ColumnPropNameInRow="TabId" msprop:Generator_ColumnPropNameInTable="TabIdColumn" type="xs:int" />
                  <xs:element name="Name" msprop:Generator_UserColumnName="Name" msprop:Generator_ColumnVarNameInTable="columnName" msprop:Generator_ColumnPropNameInRow="Name" msprop:Generator_ColumnPropNameInTable="NameColumn">
                    <xs:simpleType>
                      <xs:restriction base="xs:string">
                        <xs:maxLength value="50" />
                      </xs:restriction>
                    </xs:simpleType>
                  </xs:element>
                </xs:sequence>
              </xs:complexType>
            </xs:element>
            <xs:element name="toReadGadgets" msprop:Generator_UserTableName="toReadGadgets" msprop:Generator_RowDeletedName="toReadGadgetsRowDeleted" msprop:Generator_RowChangedName="toReadGadgetsRowChanged" msprop:Generator_RowClassName="toReadGadgetsRow" msprop:Generator_RowChangingName="toReadGadgetsRowChanging" msprop:Generator_RowEvArgName="toReadGadgetsRowChangeEvent" msprop:Generator_RowEvHandlerName="toReadGadgetsRowChangeEventHandler" msprop:Generator_TableClassName="toReadGadgetsDataTable" msprop:Generator_TableVarName="tabletoReadGadgets" msprop:Generator_RowDeletingName="toReadGadgetsRowDeleting" msprop:Generator_TablePropName="toReadGadgets">
              <xs:complexType>
                <xs:sequence>
                  <xs:element name="GadgetId" msdata:ReadOnly="true" msdata:AutoIncrement="true" msprop:Generator_UserColumnName="GadgetId" msprop:Generator_ColumnVarNameInTable="columnGadgetId" msprop:Generator_ColumnPropNameInRow="GadgetId" msprop:Generator_ColumnPropNameInTable="GadgetIdColumn" type="xs:int" />
                  <xs:element name="SearchCriteria" msprop:Generator_UserColumnName="SearchCriteria" msprop:Generator_ColumnVarNameInTable="columnSearchCriteria" msprop:Generator_ColumnPropNameInRow="SearchCriteria" msprop:Generator_ColumnPropNameInTable="SearchCriteriaColumn">
                    <xs:simpleType>
                      <xs:restriction base="xs:string">
                        <xs:maxLength value="300" />
                      </xs:restriction>
                    </xs:simpleType>
                  </xs:element>
                  <xs:element name="Rank" msprop:Generator_UserColumnName="Rank" msprop:Generator_ColumnVarNameInTable="columnRank" msprop:Generator_ColumnPropNameInRow="Rank" msprop:Generator_ColumnPropNameInTable="RankColumn" type="xs:int" />
                  <xs:element name="Title" msprop:Generator_UserColumnName="Title" msprop:Generator_ColumnVarNameInTable="columnTitle" msprop:Generator_ColumnPropNameInRow="Title" msprop:Generator_ColumnPropNameInTable="TitleColumn">
                    <xs:simpleType>
                      <xs:restriction base="xs:string">
                        <xs:maxLength value="50" />
                      </xs:restriction>
                    </xs:simpleType>
                  </xs:element>
                  <xs:element name="DisplayRows" msprop:Generator_UserColumnName="DisplayRows" msprop:Generator_ColumnVarNameInTable="columnDisplayRows" msprop:Generator_ColumnPropNameInRow="DisplayRows" msprop:Generator_ColumnPropNameInTable="DisplayRowsColumn" type="xs:int" />
                  <xs:element name="TabId" msprop:Generator_UserColumnName="TabId" msprop:Generator_ColumnVarNameInTable="columnTabId" msprop:Generator_ColumnPropNameInRow="TabId" msprop:Generator_ColumnPropNameInTable="TabIdColumn" type="xs:int" />
                  <xs:element name="TabName" msprop:Generator_UserColumnName="TabName" msprop:Generator_ColumnVarNameInTable="columnTabName" msprop:Generator_ColumnPropNameInRow="TabName" msprop:Generator_ColumnPropNameInTable="TabNameColumn">
                    <xs:simpleType>
                      <xs:restriction base="xs:string">
                        <xs:maxLength value="50" />
                      </xs:restriction>
                    </xs:simpleType>
                  </xs:element>
                </xs:sequence>
              </xs:complexType>
            </xs:element>
          </xs:choice>
        </xs:complexType>
        <xs:unique name="Constraint1" msdata:PrimaryKey="true">
          <xs:selector xpath=".//mstns:toReadTabs" />
          <xs:field xpath="mstns:TabId" />
        </xs:unique>
        <xs:unique name="toReadGadgets_Constraint1" msdata:ConstraintName="Constraint1" msdata:PrimaryKey="true">
          <xs:selector xpath=".//mstns:toReadGadgets" />
          <xs:field xpath="mstns:GadgetId" />
        </xs:unique>
      </xs:element>
    </xs:schema>

    DockStateTag.cs

    using System;
    using System.Data;
    using System.Configuration;
    using System.Web;
    using System.Web.Security;
    using System.Web.UI;
    using System.Web.UI.WebControls;
    using System.Web.UI.WebControls.WebParts;
    using System.Web.UI.HtmlControls;
      
    /// <summary>
    /// Summary description for DockStateTag
    /// </summary>
    public class DockStateTag
    {
        string _tag;
        private const string _tagDelimiter = "|";
          
        public DockStateTag(string searchCriteria, int displayRows, int tabId, string tabName)
        {
            _tag =
                searchCriteria
                + _tagDelimiter + displayRows.ToString()
                + _tagDelimiter + tabId.ToString()
                + _tagDelimiter + tabName;
        }
      
        public DockStateTag(string tag)
        {
            _tag = tag;
        }
      
        public string Tag
        {
            get { return _tag; }
        }
      
        private string[] Split()
        {
            return Tag.Split(new string[] { _tagDelimiter }, StringSplitOptions.None);
        }
      
        public string SearchCriteria
        {
            get
            {
                return Split()[0];
            }
        }
      
        public int DisplayRows
        {
            get
            {
                return int.Parse(Split()[1]);
            }
        }
      
        public int TabId
        {
            get
            {
                return int.Parse(Split()[2]);
            }
        }
      
        public string TabName
        {
            get
            {
                return Split()[3];
            }
        }
    }

    UserControls Folder

    Gadget.ascx

    <%@ Control Language="C#" AutoEventWireup="true" CodeFile="Gadget.ascx.cs" Inherits="UserControls_Gadget" %>
    <%@ Register TagPrefix="telerik" Namespace="Telerik.Web.UI" Assembly="Telerik.Web.UI" %>
    <asp:Label ID="lblDisplayRows" runat="server" Text="0" />
    <asp:Label ID="lblSearchCriteria" runat="server" />

    Gadget.ascx.cs

    using System;
    using System.Data;
    using System.Configuration;
    using System.Collections;
    using System.Web;
    using System.Web.Security;
    using System.Web.UI;
    using System.Web.UI.WebControls;
    using System.Web.UI.WebControls.WebParts;
    using System.Web.UI.HtmlControls;
    using Telerik.Web.UI;
      
    public partial class UserControls_Gadget : System.Web.UI.UserControl
    {
        protected void Page_Load(object sender, EventArgs e)
        {
        }
      
        public int DisplayRows
        {
            get { return int.Parse(lblDisplayRows.Text); }
            set { lblDisplayRows.Text = value.ToString(); }
        }
      
        public string SearchCriteria
        {
            set
            {
                lblSearchCriteria.Text = value;
            }
        }
    }

    Root Folder

    Default.aspx

    <%@ Page Language="C#" AutoEventWireup="true" CodeFile="Default.aspx.cs" Inherits="Default" %>
      
    <%@ Register TagPrefix="telerik" Namespace="Telerik.Web.UI" Assembly="Telerik.Web.UI" %>
    <%@ Register Src="~/UserControls/Gadget.ascx" TagName="Gadgets" TagPrefix="uc" %>
      
    <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
      
    <head id="Head1" runat="server">
        <title>Untitled Page</title>
    </head>
    <body>
        <form id="form1" runat="server">
            <asp:ScriptManager ID="ScriptManager1" runat="server" />
    <asp:panel id="Panel2" runat="server">
            <table width="100%">
                <tr>
                    <td colspan="2">
                        <asp:UpdatePanel runat="server" ID="UpdatePanel1">
                            <ContentTemplate>
                                <telerik:RadTabStrip ID="rtsDockTabs" runat="server" MultiPageID="rmpDockTab" />
                                <telerik:RadMultiPage ID="rmpDockTab" runat="server" SelectedIndex="0" />
                            </ContentTemplate>
                        </asp:UpdatePanel>
                    </td>
                </tr>
                <tr>
                    <td align="left">
                        <asp:Button ID="btnAdd" runat="server" Text="Add" OnClick="btnAdd_Click" />
                    </td>
                    <td align="right">
                        <asp:LinkButton ID="lbRefresh" Text="Refresh" runat="server" OnClick="lbRefresh_Click" />
                    </td>
                </tr>
            </table>
        </asp:panel>
        </form>
    </body>
    </html>

    Default.aspx.cs

    using System;
    using System.Data;
    using System.Configuration;
    using System.Collections;
    using System.Web;
    using System.Web.Security;
    using System.Web.UI;
    using System.Web.UI.WebControls;
    using System.Web.UI.WebControls.WebParts;
    using System.Web.UI.HtmlControls;
    using Telerik.Web.UI;
    using System.Collections.Generic;
      
    public partial class Default : System.Web.UI.Page
    {
        private const string _createPage = "CreateGadget.aspx?Id=";
      
        private List<DockState> CurrentDockStates
        {
            get
            {
                //Store the info about the added docks in the session. For real life
                // applications we recommend using database or other storage medium
                // for persisting this information.
                //get data
                DataLayer.toReadGadgetsDataTable gadgets = DataAccess.GetGadgets(9337);
      
                List<DockState> currentDockStates = new List<DockState>();
      
                foreach (DataRow dr in gadgets.Rows)
                {
                    DataLayer.toReadGadgetsRow row = dr as DataLayer.toReadGadgetsRow;
      
                    currentDockStates.Add(CreateDockState(row));
                }
      
                return currentDockStates;
            }
            set
            {
            }
        }
      
        private void CreateSaveStateTrigger(RadDock dock)
        {
            //Ensure that the RadDock control will initiate postback
            // when its position changes on the client or any of the commands is clicked.
            //Using the trigger we will "ajaxify" that postback.
            dock.AutoPostBack = true;
            dock.CommandsAutoPostBack = true;
      
            AsyncPostBackTrigger saveStateTrigger = new AsyncPostBackTrigger();
            saveStateTrigger.ControlID = dock.ID;
            saveStateTrigger.EventName = "DockPositionChanged";
            UpdatePanel1.Triggers.Add(saveStateTrigger);
      
            saveStateTrigger = new AsyncPostBackTrigger();
            saveStateTrigger.ControlID = dock.ID;
            saveStateTrigger.EventName = "Command";
            UpdatePanel1.Triggers.Add(saveStateTrigger);
        }
      
        private RadDock CreateRadDockFromState(DockState state)
        {
            RadDock dock = new RadDock();
            dock.DockMode = DockMode.Docked;
            dock.ID = state.UniqueName;
            dock.ApplyState(state);
            dock.Commands.Add(new DockCloseCommand());
            dock.Commands.Add(new DockExpandCollapseCommand());
      
            DockCommand dc1 = new DockCommand();
            dc1.AutoPostBack = true;
            dc1.Name = "Edit";
            dc1.Text = "Edit";
            dock.Commands.Add(dc1);
      
            dock.Command += new DockCommandEventHandler(dock_Command);
            return dock;
        }
      
        private DockState CreateDockState(DataLayer.toReadGadgetsRow row)
        {
            DockState dockState = new DockState();
            dockState.UniqueName = row.GadgetId.ToString();
            dockState.Title = row.Title;
            dockState.Width = Unit.Pixel(300);
            dockState.Height = Unit.Pixel(400);
            DockStateTag tag = new DockStateTag(row.SearchCriteria, row.DisplayRows, row.TabId, row.TabName);
            dockState.Tag = tag.Tag;
            //dockState.Index = row.Rank;
            return dockState;
        }
      
        private void Initialize()
        {
            //add all tabs
            DataLayer.toReadTabsDataTable readTabsDataTable = DataAccess.GetTabs(9337);
      
            //clear already existing tabs
            rmpDockTab.PageViews.Clear();
            rtsDockTabs.Tabs.Clear();
      
            //add tabs for user
            foreach (DataRow dr in readTabsDataTable.Rows)
            {
                DataLayer.toReadTabsRow row = (DataLayer.toReadTabsRow)dr;
                AddTab(row.Name, row.TabId);
                AddPageView(row.Name);
                CreateLayout(rmpDockTab.FindPageViewByID(row.Name));
            }
        }
      
        private void CreateLayout(RadPageView pageView)
        {
            //add raddocklayout
            RadDockLayout dockLayout = new RadDockLayout();
            dockLayout.ID = "rdlGadgets_" + pageView.ID;
            dockLayout.LoadDockLayout += new DockLayoutEventHandler(rdlGadgets_LoadDockLayout);
            dockLayout.SaveDockLayout += new DockLayoutEventHandler(rdlGadgets_SaveDockLayout);
      
            //add dock zone
            RadDockZone dockZone = new RadDockZone();
            dockZone.ID = "rdzGadgets_" + pageView.ID;
            dockZone.Orientation = Orientation.Horizontal;
            dockZone.Width = new Unit(100.0, UnitType.Percentage);
            dockZone.MinHeight =  new Unit(200);
      
            dockZone.Style["float"] = "left";
            dockZone.Style["margin-right"] = "20px";
      
            List<DockState> dockStates = CurrentDockStates;
            int count = dockStates.Count;
      
            for (int i = 0; i < count; i++)
            {
                dockStates[i].DockZoneID = dockZone.ClientID;
      
                RadDock dock = CreateRadDockFromState(dockStates[i]);
      
                DockStateTag tag = new DockStateTag(dock.Tag);
      
                //check which controls belong to this tab
                if (tag.TabName == pageView.ID)
                {
                    //We will just add the RadDock control to the RadDockLayout.
                    // You could use any other control for that purpose, just ensure
                    // that it is inside the RadDockLayout control.
                    // The RadDockLayout control will automatically move the RadDock
                    // controls to their corresponding zone in the LoadDockLayout
                    // event (see below).
      
                    //load gadget control into dock
                    UserControls_Gadget c = (UserControls_Gadget)LoadControl("~/UserControls/Gadget.ascx");
                    c.ID = tag.TabName + "_Gadget" + i.ToString();
                    c.DisplayRows = tag.DisplayRows;
                    c.SearchCriteria = tag.SearchCriteria;
      
                    dock.ContentContainer.Controls.Add(c);
      
                    //add to doc zone
                    dockZone.Controls.Add(dock);
      
                    //We want to save the dock state every time a dock is moved.
                    CreateSaveStateTrigger(dock);
                }
            }
      
            //add to layout
            dockLayout.Controls.Add(dockZone);
      
            //add to pageview
            pageView.Controls.Add(dockLayout);
        }
      
        private void AddTab(string tabName, int tabValue)
        {
            RadTab tab = new RadTab();
            tab.Text = tabName;
            tab.PageViewID = tabName;
            //tab.ID = "Tab_" + tabName;
            tab.Value = tabValue.ToString();
            rtsDockTabs.Tabs.Add(tab);
        }
      
        private void AddPageView(string id)
        {
            RadPageView pageView = new RadPageView();
            pageView.ID = id;
            rmpDockTab.PageViews.Add(pageView);
        }
      
        protected void Page_Load(object sender, EventArgs e)
        {
            //on not postback, load all docks in this event so display will occur in sequence
            //if (!IsPostBack)
            //{
            //    Initialize();
            //}
        }
      
        protected void Page_Init(object sender, EventArgs e)
        {
            //on postback, initialize dock controls so they will display
            //if (IsPostBack)
                Initialize();
        }
      
        void dock_Command(object sender, DockCommandEventArgs e)
        {
            if (sender is RadDock)
            {
                RadDock radDock = sender as RadDock;
                switch (e.Command.Name)
                {
                    case "Edit":
                        Response.Redirect(_createPage + radDock.UniqueName);
                        break;
                    case "Close":
                        break;
                }
            }
        }
      
        protected void rdlGadgets_LoadDockLayout(object sender, DockLayoutEventArgs e)
        {
            //Populate the event args with the state information. The RadDockLayout control
            // will automatically move the docks according that information.
            foreach (DockState state in CurrentDockStates)
            {
                e.Positions[state.UniqueName] = state.DockZoneID;
                e.Indices[state.UniqueName] = state.Index;
            }
        }
      
        protected void rdlGadgets_SaveDockLayout(object sender, DockLayoutEventArgs e)
        {
            //Save the dock state. This will enable us
            // to recreate the dock in the next Page_Init.
            CurrentDockStates = ((RadDockLayout)sender).GetRegisteredDocksState();
        }
      
        protected void btnAdd_Click(object sender, EventArgs e)
        {
            Response.Redirect(_createPage + "0");
        }
        protected void lbRefresh_Click(object sender, EventArgs e)
        {
        }
    }
  16. Pero
    Admin
    Pero avatar
    1156 posts

    Posted 31 Aug 2010 Link to this post

    Hello Allan,

    Thank you very much for the additional code, but still I was not able to run the code.

    As I explained in my previous reply, the issue is caused by having an empty DockZoneID of every dock, when the docks are repositioned in the LoadDockLayout event. I carefully examined the code I recommended previously, and it is not working because dockStates[i].DockZoneID = dockZone.ClientID line does not modify the CurrentDockStates property used in the rdlGadgets_LoadDockLayout handler method.

        for (int i = 0; i < count; i++)
        {
            dockStates[i].DockZoneID = dockZone.ClientID;

    Please modify your code in the following way:
    1. Make the dockStates variable global.
    2. Use dockStates instead of CurrentDockStates in the rdlGadgets_LoadDockLayout method
    3. Make sure the CreateLayout method is executed before the LoadDockLayout event is fired.

    protected void rdlGadgets_LoadDockLayout(object sender, DockLayoutEventArgs e)
    {
        //Populate the event args with the state information. The RadDockLayout control
        // will automatically move the docks according that information.
        foreach (DockState state in dockStates)
        {
            e.Positions[state.UniqueName] = state.DockZoneID;
            e.Indices[state.UniqueName] = state.Index;
        }
    }
     
    List<DockState> dockStates;
     
    private void CreateLayout(RadPageView pageView)
    {
        //add raddocklayout
        RadDockLayout dockLayout = new RadDockLayout();
        dockLayout.ID = "rdlGadgets_" + pageView.ID;
        dockLayout.LoadDockLayout += new DockLayoutEventHandler(rdlGadgets_LoadDockLayout);
        dockLayout.SaveDockLayout += new DockLayoutEventHandler(rdlGadgets_SaveDockLayout);
     
        //add dock zone
        RadDockZone dockZone = new RadDockZone();
        dockZone.ID = "rdzGadgets_" + pageView.ID;
        dockZone.Orientation = Orientation.Horizontal;
        dockZone.Width = new Unit(100.0, UnitType.Percentage);
        dockZone.MinHeight = new Unit(200);
     
        dockZone.Style["float"] = "left";
        dockZone.Style["margin-right"] = "20px";
     
     
        //add to layout
        dockLayout.Controls.Add(dockZone);
     
        //add to pageview
        pageView.Controls.Add(dockLayout);
     
        dockStates = CurrentDockStates;
        int count = dockStates.Count;
     
        for (int i = 0; i < count; i++)
        {
            dockStates[i].DockZoneID = dockZone.ClientID;
     
            RadDock dock = CreateRadDockFromState(dockStates[i]);
     
            DockStateTag tag = new DockStateTag(dock.Tag);
     
            //check which controls belong to this tab
            if (tag.TabName == pageView.ID)
            {
                //We will just add the RadDock control to the RadDockLayout.
                // You could use any other control for that purpose, just ensure
                // that it is inside the RadDockLayout control.
                // The RadDockLayout control will automatically move the RadDock
                // controls to their corresponding zone in the LoadDockLayout
                // event (see below).
     
                //load gadget control into dock
                UserControls_Gadget c = (UserControls_Gadget)LoadControl("~/UserControls/Gadget.ascx");
                c.ID = tag.TabName + "_Gadget" + i.ToString();
                c.DisplayRows = tag.DisplayRows;
                c.SearchCriteria = tag.SearchCriteria;
     
                dock.ContentContainer.Controls.Add(c);
     
                //add to doc zone
                dockZone.Controls.Add(dock);
     
                //We want to save the dock state every time a dock is moved.
                CreateSaveStateTrigger(dock);
            }
        }
    }


    I examined the code, you say adds the same docking zone twice, but did not see anywhere such code. The zone is added only once to the layout, the second to last line in the code:
    dockLayout.Controls.Add(dockZone);
    There are two loops that create a sample set of docks. The first one is executed on first load of the page, when the CurrentDockStates is empty, and the second is executed on subsequent postbacks.

    I hope this helps.

    All the best,
    Pero
    the Telerik team
    Do you want to have your say when we set our development plans? Do you want to know when a feature you care about is added or when a bug fixed? Explore the Telerik Public Issue Tracking system and vote to affect the priority of the items
  17. Allan
    Allan avatar
    10 posts
    Member since:
    Jun 2009

    Posted 31 Aug 2010 Link to this post

    Pero,

    As I mentioned before, I tried your suggestion but I still get the docks on top of one another.

    How can I help you build the code.  I belive I supplied all the necessary files.

    Alternatively, I can supply a zip of all code if needed.

    Thanks,

    Al
  18. Pero
    Admin
    Pero avatar
    1156 posts

    Posted 01 Sep 2010 Link to this post

    Hello Allan,

    To attach files other than JPEG files, you need to open a support ticket. Please open a new support ticket and send us the sample project.

    Regards,
    Pero
    the Telerik team
    Do you want to have your say when we set our development plans? Do you want to know when a feature you care about is added or when a bug fixed? Explore the Telerik Public Issue Tracking system and vote to affect the priority of the items
Back to Top
UI for ASP.NET Ajax is Ready for VS 2017