This is a migrated thread and some comments may be shown as answers.

Grid inside Combobox

4 Answers 91 Views
ComboBox
This is a migrated thread and some comments may be shown as answers.
DW Web Team Member
Top achievements
Rank 2
DW Web Team Member asked on 23 May 2011, 10:46 PM

 

Hi,

I am using grid inside combobox. Grid has the grouping and the pager. The scenario is when user selects the item of the group the selected item value is set, the combobox is collapsed, and the user is redirected to the specific places. However, when the user clicks on the group header or anywhere on the pager, the action must be completely ignored. Currently the combobox is collapsed with the empty selected value. Could you please help me to achieve the desire behavior?

Thank you, 

Tatiana

P.S. I am using v. 2009 Q3

4 Answers, 1 is accepted

Sort by
0
Gimmik
Top achievements
Rank 1
answered on 23 May 2011, 11:29 PM
Hi DW Web Team Member,

This is a pretty complex setup. I'm going to try and get a small sample working so I can see if I can reproduce your issue. I think the trick is going to be wiring-up the correct event in the combo box to cancel the close operation unless a value is selected. Tricky.

Can you provide some screen shots and/or sample code to get me started?

Thanks,
-Gimmik
0
DW Web Team Member
Top achievements
Rank 2
answered on 24 May 2011, 03:15 AM
Sure, will be happy to...
 
Here is .cs code:

using System;
using System.Collections.Generic;
using System.Web.UI;
using Telerik.Web.UI;
  
namespace GridInsideCombo
{
    public partial class Default : Page
    {
  
        private Dictionary<int, string> reportType = new Dictionary<int, string>()
        {
            {0,"Search Result"},
            {1,"Favorite"},
            {2,"Visited"}
        };
  
        [Serializable]
        private class ReportInfo
        {
            private string _name;
            private string _type;
            private int _typeOrder;
  
            public ReportInfo()
            {
            }
  
            public string Name
            {
                get { return _name; }
                set { _name = value; }
            }
            public string Type
            {
                get { return _type; }
                set { _type = value; }
            }
            public int TypeOrder
            {
                get { return _typeOrder; }
                set { _typeOrder = value; }
            }
        }
  
        private RadGrid grdReports;
  
        protected void Page_Load(object sender, EventArgs e)
        {
            grdReports = (RadGrid)(rcbSearch.Items[0].FindControl("grdReports"));
            RadAjaxManager1.AjaxSettings.AddAjaxSetting(RadAjaxManager1, grdReports, RadAjaxLoadingPanel1);
        }
  
        protected void RadAjaxManager1_AjaxRequest(object sender, AjaxRequestEventArgs e)
        {
            if (e.Argument.IndexOf("LoadFilteredData") != -1)
            {
               grdReports.Rebind();
            }
        }
  
        protected void grdReports_NeedDataSource(object source, GridNeedDataSourceEventArgs e)
        {
            RadGrid grid = (RadGrid)source;
            grid.DataSource = getGridDataSource(rcbSearch);
        }
  
        private List<ReportInfo> getGridDataSource(RadComboBox combo)
        {
            List<ReportInfo> result = new List<ReportInfo>();
            List<ReportInfo> fullList = getReportsInfo();
  
            string searchString = combo.Text.ToUpper();
            if (searchString != string.Empty)
            {
                foreach (ReportInfo report in fullList)
                {
                    if (report.Name.ToUpper().Contains(searchString))
                    {
                        result.Add(report);
                    }
                }
            }
            else
            {
                result = fullList;
            }
            return result;
        }
  
        private List<ReportInfo> getReportsInfo()
        {
            List<ReportInfo> result = new List<ReportInfo>();
            result.AddRange(createTestReports("Search", 0));
            result.AddRange(createTestReports("Favorite", 1));
            result.AddRange(createTestReports("Visited", 2));
            return result;
        }
  
        private List<ReportInfo> createTestReports(string type, int typeOrder)
        {
            List<ReportInfo> testReports = new List<ReportInfo>();
            for (int i = 0; i < 5; i++)
            {
                ReportInfo report = new ReportInfo();
                report.Name = type + " Item " + i.ToString();
                report.TypeOrder = typeOrder;
                report.Type = reportType[report.TypeOrder];
                testReports.Add(report);
            }
            return testReports;
        }
  
    }
}

And here is the aspx:
<%@ Page Language="C#" AutoEventWireup="true" EnableEventValidation="false"
    CodeBehind="Default.aspx.cs" Inherits="GridInsideCombo.Default" %>
  
<%@ Register Assembly="System.Web.Extensions, Version=3.5.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35"
    Namespace="System.Web.UI" TagPrefix="asp" %>
<%@ Register Assembly="Telerik.Web.UI" Namespace="Telerik.Web.UI" TagPrefix="telerik" %>
  
<!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></title>
        <style type="text/css">
    </style>
    <telerik:RadCodeBlock ID="RadCodeBlock2" runat="server">
        <script language="javascript" type="text/javascript">
            var grid;
  
            function dropDownOpening(sender, args) {
                $find("<%= RadAjaxManager1.ClientID %>").ajaxRequest("LoadFilteredData");
            }
  
            function dropDownKeyUp(sender) {
                var combo = $find(sender.id);
                combo.showDropDown();
            }
  
            function GridCreated(sender, args) {
                grid = sender;
                var gridHeight = sender.get_masterTableView().get_element().clientHeight;
                var combo = $find("<%= rcbSearch.ClientID %>");
                if (combo != null) {
                    var maxHeight = combo._height;
                    if (gridHeight > maxHeight) gridHeight = maxHeight;
                    combo.get_dropDownElement().style.height = gridHeight;
                }
            }
              
            function RowClicked(sender, args) {
                var combo = $find("<%= rcbSearch.ClientID %>");
                var cellValues = args.getDataKeyValue("Name");
                setTimeout(function() {
                    combo.set_text(cellValues);
                }, 50);
                combo.showDropDown();
            }
  
        </script>
    </telerik:RadCodeBlock>
</head>
<body>
    <form id="form1" runat="server">
        <telerik:RadScriptManager ID="ScriptManager1" runat="server" />
        <telerik:RadAjaxManager ID="RadAjaxManager1" runat="server" OnAjaxRequest="RadAjaxManager1_AjaxRequest">
            <ClientEvents />
            <AjaxSettings>
                <telerik:AjaxSetting AjaxControlID="grdReports">
                    <UpdatedControls>
                        <telerik:AjaxUpdatedControl ControlID="grdReports" LoadingPanelID="RadAjaxLoadingPanel1" />
                    </UpdatedControls>
                </telerik:AjaxSetting>
            </AjaxSettings>
        </telerik:RadAjaxManager>
        <telerik:RadAjaxLoadingPanel ID="RadAjaxLoadingPanel1" runat="server" />
        <table width="100%" style="margin-left: 20px; margin-top: 20px;">
            <tr style="vertical-align: top;">
                <td style="text-align: left;">
                    <telerik:RadComboBox ID="rcbSearch" runat="server" EmptyMessage="All Reports" Skin="Default"
                                        AllowCustomText="true" Width="90%" Height="500px" 
                                        MarkFirstMatch="true"
                                        ExpandAnimation-Type="None" CollapseAnimation-Type="None" 
                                        OnClientDropDownOpening="dropDownOpening" 
                                        OnKeyUp="dropDownKeyUp(this)">
                        <ItemTemplate>
                            <telerik:RadGrid runat="server" ID="grdReports" Width="99.5%" GridLines="none" Skin="Default"
                                            EnableLinqExpressions="false" 
                                            OnNeedDataSource="grdReports_NeedDataSource">
                                <ClientSettings EnableRowHoverStyle="true" Selecting-AllowRowSelect="true" 
                                                AllowKeyboardNavigation="true">
                                    <ClientEvents OnGridCreated="GridCreated" 
                                                  OnRowClick="RowClicked" />
                                </ClientSettings>
                                <MasterTableView GroupLoadMode="Client" AutoGenerateColumns="false" ShowHeader="false"
                                    TableLayout="Fixed" NoMasterRecordsText="No matches found" DataKeyNames="Name"
                                    ClientDataKeyNames="Name" AllowFilteringByColumn="false" AllowSorting="false"
                                    AllowPaging="true" PageSize="20" PagerStyle-AlwaysVisible="true" PagerStyle-Mode="NextPrevAndNumeric">
                                    <SortExpressions>
                                        <telerik:GridSortExpression FieldName="Name" SortOrder="Ascending" />
                                    </SortExpressions>
                                    <GroupByExpressions>
                                        <telerik:GridGroupByExpression>
                                            <SelectFields>
                                                <telerik:GridGroupByField FieldName="Type" HeaderText=" " HeaderValueSeparator=" " />
                                            </SelectFields>
                                            <GroupByFields>
                                                <telerik:GridGroupByField FieldName="TypeOrder" SortOrder="Ascending" />
                                            </GroupByFields>
                                        </telerik:GridGroupByExpression>
                                    </GroupByExpressions>
                                    <Columns>
                                        <telerik:GridBoundColumn DataField="Name" HeaderText="Name" UniqueName="Name" />
                                        <telerik:GridBoundColumn DataField="Type" UniqueName="Type" Visible="false" />
                                        <telerik:GridBoundColumn DataField="TypeOrder" UniqueName="TypeOrder" Visible="false" />
                                    </Columns>
                                    <ExpandCollapseColumn ItemStyle-HorizontalAlign="Left" />
                                </MasterTableView>
                            </telerik:RadGrid>
                        </ItemTemplate>
                        <Items>
                            <telerik:RadComboBoxItem runat="server" Text="" Selected="true" />
                        </Items>
                    </telerik:RadComboBox>
                </td>
            </tr>
        </table>
    </form>
</body>
</html>

Thank you for looking into it
0
Gimmik
Top achievements
Rank 1
answered on 24 May 2011, 06:06 PM
Hi DW Web Team Member,

Thanks for posting your code. I was able to get your project to run fairly easily. I've never seen a RadGrid inside of a RadComboBox, so thanks for providing the great example! I was able to work out a solution for your issue without much trouble. Before I jump into the code, I wanted to ask if you have considered other options rather then using a RadComboBox? The solution I will provide is a start, but there are a lot of events you will need to handle, and for each one either allow or disallow the RadComboBox to close. That's a lot of complexity to maintain. Perhaps a RadWindow would work better for your application. Its natural state is to stay open once it's opened, and close when you manually close it (when an item is selected.) It may also be faster when it comes to loading the RadGrid. I think it's worth a try.

Having said that, here's my solution.

To the RadComboBox I added:
OnClientDropDownClosing="rcbSearch_OnClientDropDownClosing"

I updated the ClientSettings of the RadGrid to this:
<ClientSettings EnableRowHoverStyle="true" Selecting-AllowRowSelect="true"
                AllowKeyboardNavigation="true">
    <ClientEvents OnGridCreated="GridCreated"
                  OnRowClick="RowClicked"
                  OnRowSelected="grdReports_OnRowSelected"/>
</ClientSettings>

and I added the following two JavaScript functions along with a global.
var comboOpen = true;
 
function rcbSearch_OnClientDropDownClosing(sender, args) {
    if (comboOpen) {
        args.set_cancel(true);
    }
 
}
 
function grdReports_OnRowSelected(sender, args) {
    var combo = $find("<%= rcbSearch.ClientID %>");
    comboOpen = false;
    combo.hideDropDown();
}

Basically, I cancel the closing event unless the global "comboOpen" has been set to false. This gives you complete control over when the RadComboBox can be closed.

Let me know how this works for you.

-Gimmik
0
DW Web Team Member
Top achievements
Rank 2
answered on 24 May 2011, 08:56 PM
Nice solution! Very nice!!

Thank you very much Gimmik!
Tags
ComboBox
Asked by
DW Web Team Member
Top achievements
Rank 2
Answers by
Gimmik
Top achievements
Rank 1
DW Web Team Member
Top achievements
Rank 2
Share this question
or