Dynamic TabStrip & RadDocks

3 posts, 0 answers
  1. Chris
    Chris avatar
    58 posts
    Member since:
    Feb 2012

    Posted 11 Apr 2013 Link to this post

    Hi there.

    What I'm trying to achieve here is to get a dynamic TabStrip to which I can create new tabs.
    Each of those tabs include a pageview.
    Each of those pageview embeds a usercontrol.
    Those usercontrols are consisting in a RadDockLayout + RadDockZone + a Button to create new docks on the current selected tab/pageview.

    So far nothing that sounds too fancy or hard to create. The current code works fine:

    Here's my "Default.aspx". You can notice that I'm not currently using the RadAjaxManager to Ajaxify my controls.
    In this page I'm creating my dynamic TabStrip control that let you create and close tabs via a close button.

    <%@ Page Language="C#" AutoEventWireup="true" CodeBehind="Default.aspx.cs" Inherits="Default" %>
     
    <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
    <head runat="server">
        <title></title>
        <link href="css/lines.css" rel="stylesheet" type="text/css" />
        <link href="css/colorpicker.css" rel="stylesheet" type="text/css" />
        <telerik:RadStyleSheetManager ID="RadStyleSheetManager1" runat="server" />
    </head>
    <body>
        <form id="form1" runat="server">
        <telerik:RadScriptManager ID="RadScriptManager1" runat="server">
            <Scripts>
                <asp:ScriptReference Assembly="Telerik.Web.UI" Name="Telerik.Web.UI.Common.Core.js" />
                <asp:ScriptReference Assembly="Telerik.Web.UI" Name="Telerik.Web.UI.Common.jQuery.js" />
                <asp:ScriptReference Assembly="Telerik.Web.UI" Name="Telerik.Web.UI.Common.jQueryInclude.js" />
            </Scripts>
        </telerik:RadScriptManager>
     
        <script src="js/colorpicker.js" type="text/javascript"></script>
     
        <telerik:RadCodeBlock ID="rcbLineManager" runat="server">
     
            <script type="text/javascript">
                function closeTab(tabText) {
                    try {
                        var tabStrip = $find("<%= rtsLines.ClientID %>");
                        var multiPage = $find("<%= mpLines.ClientID %>");
                        var ajaxManager = $find("<%= RadAjaxManager1.ClientID %>");
                        var tab = tabStrip.findTabByText(tabText);
                        var pageView = tab.get_pageView();
     
                        var tabToSelect = tab.get_nextTab();
                        if (!tabToSelect)
                            tabToSelect = tab.get_previousTab();
     
                        tabStrip.get_tabs().remove(tab);
                        multiPage.get_pageViews().remove(pageView);
                        if (ajaxManager != null) {
                            ajaxManager.ajaxRequest("CloseTab|" + tabText);
                        } else {
                            console.log("ajaxManager is null");
                        }
     
                        if (tabToSelect)
                            tabToSelect.set_selected(true);
                    }
                    catch (err) {
                        console.log(err.message);
                    }
                }
            </script>
     
        </telerik:RadCodeBlock>
        <telerik:RadAjaxManager ID="RadAjaxManager1" runat="server" OnAjaxRequest="RadAjaxManager1_AjaxRequest">
    <%--        <AjaxSettings>
                <telerik:AjaxSetting AjaxControlID="rbtAddLine">
                    <UpdatedControls>
                        <telerik:AjaxUpdatedControl ControlID="rtsLines"/>
                        <telerik:AjaxUpdatedControl ControlID="mpLines" LoadingPanelID="ralpLines" />
                    </UpdatedControls>
                </telerik:AjaxSetting>
            </AjaxSettings>--%>
        </telerik:RadAjaxManager>
        <telerik:RadButton ID="rbtAddLine" runat="server" OnClick="rbtAddLine_Clicked" Text="New">
        </telerik:RadButton>
        <div>
            <telerik:RadTabStrip ID="rtsLines" runat="server" CssClass="rtsLines" MultiPageID="mpLines"
                OnTabCreated="rtsLines_TabCreated">
            </telerik:RadTabStrip>
            <telerik:RadMultiPage ID="mpLines" runat="server" CssClass="multiPageViewContent"
                Height="400" Width="900" OnPageViewCreated="mpLines_PageViewCreated">
            </telerik:RadMultiPage>
            <telerik:RadAjaxLoadingPanel ID="ralpLines" runat="server">
            </telerik:RadAjaxLoadingPanel>
        </div>
        </form>
    </body>
    </html>


    Here's the code behind:
    using System;
    using System.Web;
    using System.Web.UI;
    using System.Web.UI.WebControls;
    using System.Data;
    using System.Configuration;
    using System.Web.Security;
    using System.Web.UI.WebControls.WebParts;
    using System.Web.UI.HtmlControls;
    using Telerik.Web.UI;
    using System.Collections.Generic;
    using TabsStrips.usercontrol;
     
    public partial class Default : System.Web.UI.Page
    {
        private static int _id = 0;
        private string tabName;
     
     
        protected void Page_Load(object sender, EventArgs e)
        {
             
        }
     
        protected void rbtAddLine_Clicked(object sender, EventArgs e)
        {
            try
            {
                tabName = "New_" + _id++;
                rtsLines.Tabs.Add(new RadTab(tabName));
                var pv = new RadPageView();
                pv.ID = "pv" + tabName;
                pv.Height = Unit.Pixel(200);
                pv.Width = Unit.Pixel(800);
                mpLines.PageViews.Add(pv);
            }
            catch (Exception ex)
            {
                throw;
            }
        }
     
        protected void rtsLines_TabCreated(object sender, RadTabStripEventArgs e)
        {
            try
            {
                HtmlImage img1 = new HtmlImage();
                img1.Src = "~/images/close.gif";
                img1.Attributes.Add("class", "closeTab");
                Label lbl = new Label();
                lbl.Text = e.Tab.Text;
                img1.Attributes.Add("onclick", "closeTab('" + e.Tab.Text + "');");
     
                e.Tab.Controls.Add(img1);
                e.Tab.Controls.Add(lbl);
            }
            catch (Exception ex)
            {           
                throw;
            }
        }
     
        protected void mpLines_PageViewCreated(object sender, RadMultiPageEventArgs e)
        {
            UserControl LineBuilder = (UserControl)this.LoadControl("usercontrol/LineBuilderV2.ascx");
            LineBuilder.ID = "LineBuilder_" + e.PageView.UniqueID;
            e.PageView.Controls.Add(LineBuilder);
        }
     
        protected void RadAjaxManager1_AjaxRequest(object sender, AjaxRequestEventArgs e)
        {
            try
            {
                var command = e.Argument.Split('|')[0];
                var args = e.Argument.Split('|').Length > 0 ? e.Argument.Split('|')[1] : null;
     
                switch (command)
                {
                    case "CloseTab":
                        var tab = rtsLines.FindTabByText(args, true);
                        var pv = tab.PageView;
                        rtsLines.Tabs.Remove(tab);
                        mpLines.PageViews.Remove(pv);
                        break;
                    default:
                        break;
                }
            }
            catch (Exception ex)
            {
                 
                throw;
            }
        }
    }


    Here's now the content of my usercontrol embedding the RadDockZone:
    Note that I'm using a "hidden" but still "visible" asp update panel to create my new docks, as described in most of the Telerik online examples
    <%@ Control Language="C#" AutoEventWireup="true" CodeBehind="LineBuilderV2.ascx.cs"
        Inherits="TabsStrips.usercontrol.LineBuilderV2" %>
    <telerik:RadAjaxLoadingPanel ID="RalpLineBuilder" runat="server" MinDisplayTime="500">
    </telerik:RadAjaxLoadingPanel>
    <telerik:RadScriptBlock ID="rsbLine" runat="server">
     
        <script type="text/javascript">
            $(document).ready(function() {
                var elt = $('#<%= PCommands.ClientID %>');
                var stops = $('#<%= RdzLineBuilder.ClientID %>');
                $(elt).find(".colorpicker2").ColorPicker({
                    color: '#0000ff',
                    onShow: function(colpkr) {
                        $(colpkr).fadeIn(500);
                        return false;
                    },
                    onHide: function(colpkr) {
                        $(colpkr).fadeOut(500);
                        return false;
                    },
                    onChange: function(hsb, hex, rgb) {
                        $(elt).find(".colorpicker2 div").css('backgroundColor', '#' + hex);
                        $(stops).find(".<%= RdzLineBuilder.ClientID  %>").css('backgroundColor', '#' + hex);
                    }
                });
     
                var currentLoadingPanel = null;
                var currentUpdatedControl = null;
     
                Sys.WebForms.PageRequestManager.getInstance().add_beginRequest(BeginRequestHandler);
                Sys.WebForms.PageRequestManager.getInstance().add_endRequest(EndRequestHandler);
                function BeginRequestHandler(sender, args) {
                    currentLoadingPanel = $find("<%= RalpLineBuilder.ClientID %>");
                    currentUpdatedControl = $find("<%= PLineBuilder.ClientID %>");
                    currentLoadingPanel.show(currentUpdatedControl);
                }
     
                function EndRequestHandler(sender, args) {
                    if (currentLoadingPanel != null)
                        currentLoadingPanel.hide(currentUpdatedControl);
                    currentUpdatedControl = null;
                    currentLoadingPanel = null;
                }
                 
            });
        </script>
     
    </telerik:RadScriptBlock>
    <asp:Button ID="ButtonAddStop" runat="server" OnClick="ButtonAddStop_Click" Text="Add Stop" />
    <asp:UpdatePanel ID="UpLineBuilder" runat="server" ChildrenAsTriggers="false" UpdateMode="Conditional" >
        <ContentTemplate>
            <asp:Panel ID="PLineBuilder" runat="server" Width="800px">
                <telerik:RadDockLayout ID="RdlLineBuilder" runat="server" OnSaveDockLayout="RdlLineBuilder_SaveDockLayout"
                    OnLoadDockLayout="RdlLineBuilder_LoadDockLayout">
                    <telerik:RadDockZone ID="RdzLineBuilder" runat="server" Width="100%" Height="200px"
                        Orientation="Horizontal">
                    </telerik:RadDockZone>
                </telerik:RadDockLayout>
            </asp:Panel>
        </ContentTemplate>
        <Triggers>
            <asp:AsyncPostBackTrigger ControlID="ButtonAddStop" EventName="Click" />
        </Triggers>
    </asp:UpdatePanel>
    <asp:Panel ID="PCommands" runat="server">
        <div class="colorpicker2">
            <div>
            </div>
        </div>
    </asp:Panel>
    <div style="width: 0px; height: 0px; overflow: hidden; position: absolute; left: -10000px;">
        Hidden UpdatePanel, which is used to help with saving state when minimizing, moving
        and closing docks. This way the docks state is saved faster (no need to update the
        docking zones).
        <asp:UpdatePanel ID="UpLineBuilderHidden" runat="server">
        </asp:UpdatePanel>
    </div>


    Here's the code behind:
    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Web;
    using System.Web.UI;
    using System.Web.UI.WebControls;
    using Telerik.Web.UI;
    using System.Web.UI.HtmlControls;
     
    namespace TabsStrips.usercontrol
    {
        public partial class LineBuilderV2 : System.Web.UI.UserControl
        {
            private string _suffixID;
     
            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.
                    List<DockState> _currentDockStates = (List<DockState>)Session["CurrentDockStates_" + this.ID];
                    if (Object.Equals(_currentDockStates, null))
                    {
                        _currentDockStates = new List<DockState>();
                        Session["CurrentDockStates_" + this.ID] = _currentDockStates;
                    }
                    return _currentDockStates;
                }
                set
                {
                    Session["CurrentDockStates_" + this.ID] = value;
                }
            }
     
     
            protected void Page_Load(object sender, EventArgs e)
            {
                _suffixID = this.ClientID.Replace("-", "").Replace("$", "");
                this.Page.LoadComplete += new EventHandler(Page_LoadComplete);
            }
     
            void Page_LoadComplete(object sender, EventArgs e)
            {
                ScriptManager.RegisterStartupScript(this, this.GetType(), "LineBuilder_" + _suffixID,
                    @"var currentLoadingPanel = null;
                      var currentUpdatedControl = null;
     
                      Sys.WebForms.PageRequestManager.getInstance().add_beginRequest(BeginRequestHandler);
                      Sys.WebForms.PageRequestManager.getInstance().add_endRequest(EndRequestHandler);
                      function BeginRequestHandler(sender, args) {
                          currentLoadingPanel = $('#" + RalpLineBuilder.ClientID + @"');
                          currentUpdatedControl = $('#" + PLineBuilder.ClientID + @"');
                          currentLoadingPanel.show(currentUpdatedControl);
                      }
     
                      function EndRequestHandler(sender, args) {
                          if (currentLoadingPanel != null)
                              currentLoadingPanel.hide(currentUpdatedControl);
                          currentUpdatedControl = null;
                          currentLoadingPanel = null;
                      }", true);
            }
     
            protected void Page_Init(object sender, EventArgs e)
            {
                //Recreate the docks in order to ensure their proper operation
                for (int i = 0; i < CurrentDockStates.Count; i++)
                {
                    RadDock dock = CreateRadDockFromState(CurrentDockStates[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).
                    RdlLineBuilder.Controls.Add(dock);
                    //We want to save the dock state every time a dock is moved.
                    CreateSaveStateTrigger(dock);
     
                    if (CurrentDockStates[i].Closed == true)
                    {
                        dock.Visible = false;
                    }
                }
            }
     
            protected void RdlLineBuilder_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 RdlLineBuilder_SaveDockLayout(object sender, DockLayoutEventArgs e)
            {
                //Save the dock state in the session. This will enable us
                // to recreate the dock in the next Page_Init.
                CurrentDockStates = RdlLineBuilder.GetRegisteredDocksState();
            }
     
            private RadDock CreateRadDockFromState(DockState state)
            {
                HtmlGenericControl div = new HtmlGenericControl("div");
                div.Attributes.Add("class", RdzLineBuilder.ClientID);
                div.Style.Add("width", "100px");
                div.Style.Add("height", "100px");
                div.Style.Add("background-color", "White");
     
                RadDock dock = new RadDock();
                dock.DockMode = DockMode.Docked;
                dock.ID = string.Format("RadDock{0}", state.UniqueName);
                dock.ApplyState(state);
                dock.ContentContainer.Controls.Add(div);
                dock.Command += new DockCommandEventHandler(dock_Command);
                dock.Commands.Add(new DockCloseCommand());
     
                return dock;
            }
     
            void dock_Command(object sender, DockCommandEventArgs e)
            {
                if (e.Command.Name == "Close")
                {
                    ScriptManager.RegisterStartupScript(
                    UpLineBuilderHidden,
                    this.GetType(),
                    "RemoveDock",
                    string.Format(@"function _removeDock() {{ 
                                    Sys.Application.remove_load(_removeDock); 
                                    $find('{0}').undock(); 
                                    $get('{1}').appendChild($get('{0}')); 
                                    $find('{0}').doPostBack('DockPositionChanged'); 
                                    }}; 
                                    Sys.Application.add_load(_removeDock);", ((RadDock)sender).ClientID, UpLineBuilderHidden.ClientID),
                                  true);
                    CurrentDockStates.Remove(((RadDock)sender).GetState());
                }
            }
     
            private RadDock CreateRadDock()
            {
                HtmlGenericControl div = new HtmlGenericControl("div");
                div.Attributes.Add("class", RdzLineBuilder.ClientID);
                div.Style.Add("width", "100px");
                div.Style.Add("height", "100px");
                div.Style.Add("background-color", "White");
     
                RadDock dock = new RadDock();
                dock.DockMode = DockMode.Docked;
                dock.UniqueName = Guid.NewGuid().ToString().Replace("-", "a");
                dock.ID = string.Format("RadDock{0}", dock.UniqueName);
                dock.Title = "Stop";
                dock.Text = string.Format("Added at {0}\n{1}", DateTime.Now, dock.UniqueName);
                dock.ContentContainer.Controls.Add(div);
                dock.Width = Unit.Pixel(220);
                dock.Height = Unit.Pixel(200);
                dock.Command += new DockCommandEventHandler(dock_Command);
                dock.Commands.Add(new DockCloseCommand());
     
                return dock;
            }
     
            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";
                UpLineBuilderHidden.Triggers.Add(saveStateTrigger);
     
                saveStateTrigger = new AsyncPostBackTrigger();
                saveStateTrigger.ControlID = dock.ID;
                saveStateTrigger.EventName = "Command";
                UpLineBuilderHidden.Triggers.Add(saveStateTrigger);
            }
     
            protected void ButtonAddStop_Click(object sender, EventArgs e)
            {
                RadDock dock = CreateRadDock();
                //adding the dock to the docklayout and then docking it to the zone to avoid ViewState issues on subsequent postback
                RdlLineBuilder.Controls.Add(dock);
                //UpLineBuilderHidden.ContentTemplateContainer.Controls.Add(dock);
     
                ScriptManager.RegisterStartupScript(
                dock,
                this.GetType(),
                "AddDock",
                string.Format(@"function _addDock() {{ 
                                    Sys.Application.remove_load(_addDock); 
                                    $find('{1}').dock($find('{0}'),{2});  
                                    $find('{0}').doPostBack('DockPositionChanged'); 
                                    }}; 
                                    Sys.Application.add_load(_addDock);", dock.ClientID, RdzLineBuilder.ClientID, 0),
                                                                        true);
     
                CreateSaveStateTrigger(dock);
            }
        }
    }


    As I said, this works fine. But what I want to achieve is to ajaxify the whole lot, i.e Use my RadAjaxManager on my default.aspx page.
    Right now, as soon as I create a new tab, it postback the page and I'm losing some info (plus the page flicks on Chrome, FF is alright)

    If I enable my AjaxManager I get the following error message that plenty of people have seen before:
    "Sys.InvalidOperationException: Sys.InvalidOperationException: Could not find UpdatePanel with ID 'LineBuilder_pvNew_0_UpLineBuilderHidden'. If it is being updated dynamically then it must be inside another UpdatePanel"

    Although I've found many people with the same issue of having an Update Panel within an Ajaxified usercontrol (see here for Telerik explanation) I can't get my mind around this to get a fully ajaxify project.

    Another behavior I would like to code is to get an horizontal scrolling bar to appear when adding new docks rather than having them stacking on a new row and a vertical scroll bar.

    You can download the project source as zip from here

    Any idea / help would be much appreciated.

    Cheers everyone,

    Chris
  2. Chris
    Chris avatar
    58 posts
    Member since:
    Feb 2012

    Posted 12 Apr 2013 Link to this post

    Ok, As I suspected the issue came from my Update Panels in my usercontrols. So I got rid of those and registered my Button, Panel and Loading panel with the RadAjaxManager from my main page. Here's how my usercontrol looks like now:

    Note that there is no more UpdatePanels
    <%@ Control Language="C#" AutoEventWireup="true" CodeBehind="LineBuilderV2.ascx.cs"
        Inherits="TabsStrips.usercontrol.LineBuilderV2" %>
    <telerik:RadAjaxLoadingPanel ID="RalpLineBuilder" runat="server" MinDisplayTime="500">
    </telerik:RadAjaxLoadingPanel>
    <telerik:RadScriptBlock ID="rsbLine" runat="server">
     
        <script type="text/javascript">
            $(document).ready(function() {
                var elt = $('#<%= PCommands.ClientID %>');
                var stops = $('#<%= RdzLineBuilder.ClientID %>');
                $(elt).find(".colorpicker2").ColorPicker({
                    color: '#0000ff',
                    onShow: function(colpkr) {
                        $(colpkr).fadeIn(500);
                        return false;
                    },
                    onHide: function(colpkr) {
                        $(colpkr).fadeOut(500);
                        return false;
                    },
                    onChange: function(hsb, hex, rgb) {
                        $(elt).find(".colorpicker2 div").css('backgroundColor', '#' + hex);
                        $(stops).find(".<%= RdzLineBuilder.ClientID  %>").css('backgroundColor', '#' + hex);
                    }
                });
                 
            });
        </script>
     
    </telerik:RadScriptBlock>
    <asp:Button ID="ButtonAddStop" runat="server" OnClick="ButtonAddStop_Click" Text="Add Stop" />
            <asp:Panel ID="PLineBuilder" runat="server" Width="800px">
                <telerik:RadDockLayout ID="RdlLineBuilder" runat="server" OnSaveDockLayout="RdlLineBuilder_SaveDockLayout"
                    OnLoadDockLayout="RdlLineBuilder_LoadDockLayout">
                    <telerik:RadDockZone ID="RdzLineBuilder" runat="server" Width="100%" Height="200px"
                        Orientation="Horizontal">
                    </telerik:RadDockZone>
                </telerik:RadDockLayout>
            </asp:Panel>
    <asp:Panel ID="PCommands" runat="server">
        <div class="colorpicker2">
            <div>
            </div>
        </div>
    </asp:Panel>


    And in code behind:
    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Web;
    using System.Web.UI;
    using System.Web.UI.WebControls;
    using Telerik.Web.UI;
    using System.Web.UI.HtmlControls;
     
    namespace TabsStrips.usercontrol
    {
        public partial class LineBuilderV2 : System.Web.UI.UserControl
        {
            private string _suffixID;
     
            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.
                    List<DockState> _currentDockStates = (List<DockState>)Session["CurrentDockStates_" this.ID];
                    if (Object.Equals(_currentDockStates, null))
                    {
                        _currentDockStates = new List<DockState>();
                        Session["CurrentDockStates_" this.ID] = _currentDockStates;
                    }
                    return _currentDockStates;
                }
                set
                {
                    Session["CurrentDockStates_" this.ID] = value;
                }
            }
     
     
            protected void Page_Load(object sender, EventArgs e)
            {
                _suffixID = this.ClientID.Replace("-""").Replace("$""");
            }
     
            protected void Page_Init(object sender, EventArgs e)
            {
                RadAjaxManager.GetCurrent(this.Page).AjaxSettings.AddAjaxSetting(ButtonAddStop, PLineBuilder, RalpLineBuilder);
                //Recreate the docks in order to ensure their proper operation
                for (int i = 0; i < CurrentDockStates.Count; i++)
                {
                    RadDock dock = CreateRadDockFromState(CurrentDockStates[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).
                    RdlLineBuilder.Controls.Add(dock);
                    //We want to save the dock state every time a dock is moved.
                    CreateSaveStateTrigger(dock);
                    if (CurrentDockStates[i].Closed == true)
                    {
                        dock.Visible = false;
                    }
                }
            }
     
            protected void RdlLineBuilder_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 RdlLineBuilder_SaveDockLayout(object sender, DockLayoutEventArgs e)
            {
                //Save the dock state in the session. This will enable us
                // to recreate the dock in the next Page_Init.
                CurrentDockStates = RdlLineBuilder.GetRegisteredDocksState();
            }
     
            private RadDock CreateRadDockFromState(DockState state)
            {
                HtmlGenericControl div = new HtmlGenericControl("div");
                div.Attributes.Add("class", RdzLineBuilder.ClientID);
                div.Style.Add("width""100px");
                div.Style.Add("height""100px");
                div.Style.Add("background-color""White");
     
                RadDock dock = new RadDock();
                dock.DockMode = DockMode.Docked;
                dock.ID = string.Format("RadDock{0}", state.UniqueName);
                dock.ApplyState(state);
                dock.ContentContainer.Controls.Add(div);
                dock.Command += new DockCommandEventHandler(dock_Command);
                dock.Commands.Add(new DockCloseCommand());
     
                return dock;
            }
     
            void dock_Command(object sender, DockCommandEventArgs e)
            {
                if (e.Command.Name == "Close")
                {
                    ScriptManager.RegisterStartupScript(
                    PLineBuilder,
                    this.GetType(),
                    "RemoveDock",
                    string.Format(@"function _removeDock() {{ 
                                    Sys.Application.remove_load(_removeDock); 
                                    $find('{0}').undock(); 
                                    $get('{1}').appendChild($get('{0}')); 
                                    $find('{0}').doPostBack('DockPositionChanged'); 
                                    }}; 
                                    Sys.Application.add_load(_removeDock);", ((RadDock)sender).ClientID, PLineBuilder.ClientID),
                                  true);
                    CurrentDockStates.Remove(((RadDock)sender).GetState());
                }
            }
     
            private RadDock CreateRadDock()
            {
                HtmlGenericControl div = new HtmlGenericControl("div");
                div.Attributes.Add("class", RdzLineBuilder.ClientID);
                div.Style.Add("width""100px");
                div.Style.Add("height""100px");
                div.Style.Add("background-color""White");
     
                RadDock dock = new RadDock();
                dock.DockMode = DockMode.Docked;
                dock.UniqueName = Guid.NewGuid().ToString().Replace("-""a");
                dock.ID = string.Format("RadDock{0}", dock.UniqueName);
                dock.Title = "Stop";
                dock.Text = string.Format("Added at {0}\n{1}", DateTime.Now, dock.UniqueName);
                dock.ContentContainer.Controls.Add(div);
                dock.Width = Unit.Pixel(220);
                dock.Height = Unit.Pixel(200);
                dock.Command += new DockCommandEventHandler(dock_Command);
                dock.Commands.Add(new DockCloseCommand());
     
                return dock;
            }
     
            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;
                // still need to work on that part
            }
     
     
            protected void ButtonAddStop_Click(object sender, EventArgs e)
            {
                RadDock dock = CreateRadDock();
                //adding the dock to the docklayout and then docking it to the zone to avoid ViewState issues on subsequent postback
                RdlLineBuilder.Controls.Add(dock);
                dock.Dock(RdzLineBuilder);
     
                ScriptManager.RegisterStartupScript(
                dock,
                this.GetType(),
                "AddDock",
                string.Format(@"function _addDock() {{ 
                                    Sys.Application.remove_load(_addDock); 
                                    $find('{1}').dock($find('{0}'),{2});  
                                    $find('{0}').doPostBack('DockPositionChanged'); 
                                    }}; 
                                    Sys.Application.add_load(_addDock);", dock.ClientID, RdzLineBuilder.ClientID, 0),
                                                                        true);
     
                CreateSaveStateTrigger(dock);
            }
        }
    }

    Works like a charm now.

    Now I need to make this TabStrip persistent on refresh. Does anyone kow if the new Persistent Framework can be of any help here ?

    Thanks

    Chris
  3. UI for ASP.NET Ajax is Ready for VS 2017
  4. Helen
    Admin
    Helen avatar
    1052 posts

    Posted 12 Apr 2013 Link to this post

    Hello Chris,

    With Persistence Framework you may save and load particular tab selected. More information you may find here:
    http://www.telerik.com/help/aspnet-ajax/persistence-framework-supported-controls.html


    Regards,
    Helen
    the Telerik team
    If you want to get updates on new releases, tips and tricks and sneak peeks at our product labs directly from the developers working on the RadControls for ASP.NET AJAX, subscribe to their blog feed now.
Back to Top