0

I am binding ASP.Net Grid View with list object. I have created Country and City Class inherited from their respective interface.

public interface ICountry
{
    int cmID { get; set; }
    string cmName { get; set; }        
}

public interface ICity 
{
    int ctyId { get; set; }
    string ctyName { get; set; }    
}

public class Country : ICountry
{
    public int cmID { get; set; }
    public string cmName { get; set; }     
}

 public class City : ICity
{
    public int ctyId { get; set; }
    public string ctyName { get; set; }
    public ICountry Country { get; set; }   


public List<City> GetAllCity(string SortDirection, string SortExpression)
{
   DataTable dt = FillCity()            //returns city,country in a table
   List<City> obj = new List<City>();          
   foreach(DataRow dr in dt.Rows)
   {
       City o = new City();
       o.ctyName = dr["ctyName"].ToString();
       o.Country.cmName = dr["cmName"].ToString();
       obj.Add(o);
   }

       dt.Dispose();
       return obj;          
}


    <asp:GridView ID="GridView1" runat="server" Width="100%" AutoGenerateColumns="false" PageSize="15"
AllowPaging="true" OnPageIndexChanging="GRV1_PageIndexChanging"
AllowSorting="true" onsorting="GRV1_Sorting">                                    
<Columns>
    <asp:TemplateField ItemStyle-Width="10%" ItemStyle-HorizontalAlign="Left" HeaderText="City" SortExpression="ctyName ">
        <ItemTemplate>
            <%# Eval("ctyName")%>
        </ItemTemplate>
    </asp:TemplateField>
    <asp:TemplateField ItemStyle-Width="15%" ItemStyle-HorizontalAlign="Left" HeaderText="Country" SortExpression="Country.cmName">
        <ItemTemplate>
            <%# Eval("Country.cmName")%>
        </ItemTemplate>
    </asp:TemplateField>
</Columns></asp:GridView>

I have tried to sort using Linq but failed to do so. How can I sort data in a grid view using List ?

I have tried using following but didn't work

            if (obj != null)
        {

            var param = Expression.Parameter(typeof(MemorandaClosing), SortExpression);
            var sortExpression = Expression.Lambda<Func<MemorandaClosing, object>>(Expression.Convert(Expression.Property(param, SortExpression), typeof(object)), param);

            if (SortDirection == "ASC")
            {
                obj.AsQueryable<MemorandaClosing>().OrderBy(sortExpression);
            }
            else
            {
                obj.AsQueryable<MemorandaClosing>().OrderByDescending(sortExpression);
            };
        }
Shekhar Dalvi
  • 209
  • 6
  • 15

5 Answers5

0

try like this in method GetAllCity()

this will order by CityName

return obj.OrderBy(x => x.ctyName).ToList();  
Just code
  • 13,553
  • 10
  • 51
  • 93
Dgan
  • 10,077
  • 1
  • 29
  • 51
  • what If I have to pass Sort Expression and Sort Direction to the GetAllCity() method. Like what if I need to sort using Country Name? – Shekhar Dalvi Jul 19 '14 at 06:46
0

In adition for what @Ganesh_Devlekar have said, you can order too by descencing using:

return obj.OrderByDescending(x => x.ctyName).ToList()

And even do some kind of filter using Where or something ;)

I hope this helps

Oscar Bralo
  • 1,912
  • 13
  • 12
0

If you are wanting to sort on possibly two different fields, you will need something a bit more complicated. Specifically, you would need to specify to the GetAllCity() method which field(s) you wish to sort on. Here is one possible approach (admittedly not the most elegant):

public List<City> GetAllCity(bool SortOnCity, bool SortOnCountry)
{
    //main code omitted for brevity

    if (SortOnCity && !SortOnCountry)
        return obj.OrderBy(x => x.ctyName).ToList();
    else if (SortOnCountry && !SortOnCity)
        return obj.OrderBy(x => x.Country.cmName).ToList();
    else if (SortOnCity && SortOnCountry)
        return obj.OrderBy(x => new {x.ctyName, x.Country.cmName}).ToList();
}

For my money, I would be instead passing in a lambda expression parameter which gets passed through to the OrderBy method, rather than having such a dirty if...else...else, but I think the above code demonstrates the concepts better.

To rewrite the above code passing in the SortOrder and SortExpression as variables you would do something like the following:

public List<City> GetAllCity<TKey>(SortDirection order, Expression<Func<City, TKey>> SortExpression)
{
    //main code omitted for brevity

    if (order == SortDirection.Ascending)
        return obj.OrderBy(SortExpression);
    else
        return obj.OrderByDescending(SortExpression);

}

You would then pass in a lambda expression representing the properties you want to sort on, similar to:

GetAllCity(SortDirection.Ascending, c => new {c.ctyName, c.Country.cmName});

Please note that this is just an example and may need tweaking to your particular situation.

Katstevens
  • 1,556
  • 13
  • 29
0

Sorting has to be taken care of manually. And it can be complicated based on your requirement - say if you want a 3-level sorting. Assuming you want to sort data with reference to a single field. You would need to do the following:

  1. Keep track of the sort direction in ViewState
  2. Handle the GridView's sorting event, and query the data appropriately from the backend.

Here is a sample snippet adapted from here:

public SortDirection GridViewSortDirection
{
    get
    {
        if (ViewState["sortDirection"] == null)
            ViewState["sortDirection"] = SortDirection.Ascending;

        return (SortDirection)ViewState["sortDirection"];
    }
    set { ViewState["sortDirection"] = value; }
}

protected void gridView_Sorting(object sender, GridViewSortEventArgs e)
{           
    if (GridViewSortDirection == SortDirection.Ascending)
    {
        myGridView.DataSource = GetData(e.SortExpression, SortDirection.Ascending);
        GridViewSortDirection = SortDirection.Descending;
    }
    else
    {
        myGridView.DataSource = GetData(e.SortExpression, SortDirection.Descending);
        GridViewSortDirection = SortDirection.Ascending;
    };
    myGridView.DataBind();        
}
Community
  • 1
  • 1
deostroll
  • 11,661
  • 21
  • 90
  • 161
0

Thanks Guys for providing me hints for the solution to my questions. Here I found the post in stack overflow which works perfect in my case.

Building an OrderBy Lambda expression based on child entity's property

Community
  • 1
  • 1
Shekhar Dalvi
  • 209
  • 6
  • 15