Click here to Skip to main content
Click here to Skip to main content

Groupable ListView

By , 15 Sep 2006
 

Sample Image - GroupableListView.png

Introduction

Some time ago, I thought about writing a small extension to the ListView control. This would dynamically create a graphic user interface to allow the end-user create/modify groups, something like ‘GROUP BY’ in SQL. The control will automatically create a ToolStrip and a ToolStripButton for each column.

Usage

To use the control, just add ExListView.cs to your project, and switch the GroupsGUIs property to true, if you want to give the possibility to group items for the users.

Properties

  • GroupsGUIs - Show or not the ToolStrip to allow group items.
  • ToolStripImage - The image to show on ToolStripButtons of the groups.
  • ShowGroupLabel - Show or hide the 'ShowGroup' label.
  • ShowGroupLabelText - The 'ShowGroup' label. Default: 'Group by:'.

Example

I prepared a small example project, with a ListView which contains some employees. Each employee has a name, sex, and a job. So, if the user wants to group the employees by sex, he just needs to press one button, and the ListView will analyze each ListViewItem and create groups for the data. It creates one group for each different data in selected colums.

Here you see an example of ListView, grouped by Sex and Job:

Sample Image - GroupableListView.png

Code

To analyze and create the groups, I wrote a GroupBy(ColumnHeader[] Headers) method, it’s a simple thread-safe method with a few loops which add groups for each new different data found.

delegate void dGroupBy(ColumnHeader[] Headers);
public void GroupBy(ColumnHeader[] Headers)
{
    if (this.InvokeRequired)
    {
        dGroupBy d = new dGroupBy(GroupBy);
        this.Invoke(d, new object[] { Headers });
    }
    else
    {
        //code
        foreach (ListViewItem lvi in this.Items)
        {
            string header = "";

            foreach (ColumnHeader ch in Headers)
            {
                header += " " + 
                   lvi.SubItems[ch.Index].Text;
            }
            ListViewGroup group = 
                new ListViewGroup(header);
            ListViewGroup found = null;
            foreach (ListViewGroup g in Groups)
            {
                if (g.Header == group.Header)
                { found = g; break; }
            }
            if (found == null)
            {
                this.Groups.Add(group);
                group.Items.Add(lvi);
            }
            else
            {
                found.Items.Add(lvi);
            }
        }
    }
}

Sample Image - GroupableListView.png

History

  • 06/09/06 – v.1.01: Dock fill bug fixed.
  • 20/08/06 – Initial release.

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)

About the Author

Kel_
Chief Technology Officer Misakai Ltd.
Ireland Ireland
Member
Roman Atachiants is the guy behind www.spike-engine.com project, a real-time, client-server networking layer (SOA, RPC) for .NET developers.
 
He is a software engineer and scientist with extensive experience in different computer science domains, programming languages/principles/patterns & frameworks.
 
His main expertise consists of C# and .NET platform, game technologies, cloud, human-computer interaction, big data and artificial intelligence. He has an extensive programming knowledge and R&D expertise.

 

Sign Up to vote   Poor Excellent
Add a reason or comment to your vote: x
Votes of 3 or less require a comment

Comments and Discussions

 
You must Sign In to use this message board.
Search this forum  
    Spacing  Noise  Layout  Per page   
GeneralVery nice extension!memberSam Jacobs17 Mar '10 - 12:40 
Works great! Have a quick question ...
I'm trying to add a line or 2 of explanatory text above the tabstrip.
Although I can see it at design time, when I run the app, the text disappears (even though I modified the co-ordinates of the control). Any ideas what I might be missing? Thanks!
Generalwrite text in GroupingmemberRohit Mahajan21 May '08 - 21:39 
Hello
 
Is it possible to write text in Grouping like
 
TESTING
---------------------------------
 
Whats going on?
 
to
 
TESTING
--------------------
whats
going
on?
 
where it is one Text only?
GeneralVista Style Group/SortmemberAlexandru Stanciu27 Feb '08 - 17:54 
Any idea on how to get something like the Windows Vista Explorer ListView with the nice per column Sort/Group feature?
QuestionNo scroll barmemberBill W15 Nov '07 - 4:29 
I really like your group by list view. It saved me the hassle of having to figure this out and write it myself Smile | :) !
 
One thing I'm seeing though is that when I have a large number of items in the list with the groups, the scroll bars do not appear, even though the setting on the control is to show scrollbars.
 
Any idea why the scroll bar will not show up?
 
Thanks.
 
Bill
QuestionStrange Issuemember-_-_-_-_-_22 Aug '07 - 21:10 
HI.
 
I like this control a lot, but i have a issue with it, and for the life of me, i can't figure out what the problem is.
i load up a XML file in my program. (around 15 records).
I then add the items to the list:
 
foreach (base_Item bi in Items)
{
dlg.pb_Progress.PerformStep();
 
ListViewItem lvi = new ListViewItem(bi.Type, bi.IconNum);
lvi.SubItems.Add(bi.Name_Short);
lvi.SubItems.Add(bi.Description_Short);
lvi.SubItems.Add(bi.Genre);
lvi.SubItems.Add(bi.NumberOfDisks.ToString());
lvi.SubItems.Add(bi.Format);
lvi.SubItems.Add(bi.Reference);
elv.Items.Add(lvi);
}

 
this is a valid way of adding to a list. but when i do it, there is nothing shown in the list. it is all clear. Yet, when i just create a temporary ListView (just a standard one), and give it this identical code, (of course change the name), it all shows up fine. I have had it working 100%, and then it just stops working. i even set up some temporary ExListViews, and it does the same thing. really strange. i would love to use this control, but at this stage it's not suitable Frown | :( .
Any suggestions ?
Thanks
AnswerRe: Strange Issuemember-_-_-_-_-_22 Aug '07 - 21:18 
I also as an experiment, renamed the ExListView to lv_test, and a standard ListView to elv. and didn't change any code, and the same results, the ListView has nice data, and the ExListView has nothing - so that means that the code works fine. Strange..
QuestionWidth-Problem when ListView in LargeIcon-ModememberStephan Mantel17 Jun '07 - 3:21 
Hello,
 
First of all let me say that I really like your control. It's exactly what I was looking for.
 
But I have a strange problem when I use the ListView in LargeIcon-Mode (myView.View = LargeIcon) and use the grouping feature. When there is no grouping, the items are displayed correctly. But when I group them, the items are displayed with a very large gap between them. E.g. when without grouping 5 items are displayed in one row, with grouping only 2 items are displayed, because of a large gap between them. I tried to change the column width property, but that had no effect.
 
Does anyone has a clue, how I can solve this? Every hint is welcome. Wink | ;-)
 
Thanx in advance.
Stephan
GeneralGrouping Sortedmemberchancer10116 May '07 - 4:56 
Let me start by saying I love this control, just made an enhancement which I thought I'd share with you all.....
 
When clicking on one of the "grouping" buttons, the order seems to be from the first item in each group, not by the group name. Smile | :)
 
Modify the GroupBy method to include the following calls to the ListViewGroupSorter
 
public void GroupBy(ColumnHeader[] Headers)
{
if (this.InvokeRequired)
{
dGroupBy d = new dGroupBy(GroupBy);
try
{
this.Invoke(d, new object[] { Headers });
}
catch (Exception ex)
{

//throw;
return;
}

}
else
{
//code
foreach (ListViewItem lvi in this.Items)
{
string header = "";
 
foreach (ColumnHeader ch in Headers)
{
header += lvi.SubItems[ch.Index].Text + " / ";
}
 
ListViewGroup group = new ListViewGroup(header);
ListViewGroup found = null;
 
foreach (ListViewGroup g in Groups)
{
if (g.Header == group.Header)
{ found = g; break; }
}
if (found == null)
{
this.Groups.Add(group);
group.Items.Add(lvi);

}
else
{
found.Items.Add(lvi);
}
}
 
// Copy the groups for the column to an array.
ListViewGroup[] groupsArray = new ListViewGroup[Groups.Count];
Groups.CopyTo(groupsArray, 0);
 
// Sort the groups and add them to myListView.
Array.Sort(groupsArray, new ListViewGroupSorter(SortOrder.Ascending));
this.Groups.Clear();
this.Groups.AddRange(groupsArray);

}
}
 

 
and added this class (from MSDN) to the control
 
// Sorts ListViewGroup objects by header value.
public class ListViewGroupSorter : IComparer
{
private SortOrder order;
 
// Stores the sort order.
public ListViewGroupSorter(SortOrder theOrder)
{
order = theOrder;
}
 
// Compares the groups by header value, using the saved sort
// order to return the correct value.
public int Compare(object x, object y)
{
int result = String.Compare(
((ListViewGroup)x).Header,
((ListViewGroup)y).Header
);
if (order == SortOrder.Ascending)
{
return result;
}
else
{
return -result;
}
}
}
GeneralSeem a bugmemberdvptUml3 Apr '07 - 16:05 
Sorry, i'm not a programmer, just a financial manager !! and i never wrote an article (not enough time to learn programming...).
But i think i've found that bug : when you set a group and then unset it (and nor category is set), the border line still appear.
May I suggest to add in the void tsb_Click(object sender, EventArgs e) method after HeaderGroup.Remove... the following:
if (HeaderGroup.Count == 0)
{
  this.Group.Clear();
  return; // nothing to ask 'GroupBy'
}
I hope i'm not wrong since nobody told this ....
 
Not a programmer but DvptUml is my credo
Generaluse combobox instead of a toolstrip... [modified]memberTheCardinal17 Oct '06 - 21:04 
i it possible to use or support combobox instead of using a toolstrip.
 
it would be nice to use a combobox for the selection of columns to group instead of using a toolstrip Smile | :)
 
anyway just a request.
 
Excellent control and keep up the good work Smile | :)
 

-- modified at 14:39 Thursday 19th October, 2006

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Rant Rant    Admin Admin   

Permalink | Advertise | Privacy | Mobile
Web02 | 2.6.130523.1 | Last Updated 15 Sep 2006
Article Copyright 2006 by Kel_
Everything else Copyright © CodeProject, 1999-2013
Terms of Use
Layout: fixed | fluid