locked
Fixed Column Wrap Panel??? RRS feed

  • Question

  •  

    I need to have an items control / list box, where I can specify a fixed number of instances per row, with equal widths, such that if a I bind a collection with X number of items, the number of rows would be # items / # instances per row.  For example:

     List<MyClass> MyClasses = new List<MyClass> ()

    {

     new MyClass {...}

    ...

    }

    Display

    Instance     Instance     Instance

    Instance     Instance     Instance

    Instance     Instance     Instance

    Instance     ...

    Is there anyway to do this without writing a custom panel or control???

     

     

    Saturday, October 11, 2008 9:05 PM

Answers

  • I solved the problem myself by creating a custom panel.

    Here it is:

    public class FixedColumnPanel : Panel

    {

    public static readonly DependencyProperty ColumnCountProperty = DependencyProperty.Register ("ColumnCount", typeof (int), typeof (FixedColumnPanel), null);
    public int ColumnCount

    {

    get { return (int)GetValue (ColumnCountProperty); }

    set { SetValue (ColumnCountProperty, value); }

    }

    protected override Size MeasureOverride (Size AvailableSize)

    {

    foreach (var Child in Children)

    {

    Child.Measure (AvailableSize);

    }

    return (new Size (100, 100));

     

    }

    protected override Size ArrangeOverride (Size FinalSize)

    {

    int RowCount = 0;

    int CurrentRow = 0;

    double AverageHeight = 0;

    double TotalHeight = 0;

    double ColumnWidth = FinalSize.Width / ColumnCount;

    int CurrentColumn = 0;

    foreach (var Child in Children)

    {

    TotalHeight += Child.DesiredSize.Height;

    if (++CurrentColumn > ColumnCount)

    {

    RowCount++;

    CurrentColumn = 1;

    }

    }

    AverageHeight = TotalHeight / ColumnCount / RowCount;

    CurrentColumn = 0;

     

    foreach (var Child in Children)

    {

    if (++CurrentColumn > ColumnCount)

    {

    CurrentColumn = 1;

    CurrentRow++;

    }

    TotalHeight += Child.DesiredSize.Height;

    var FinalRect = new Rect (ColumnWidth * (CurrentColumn-1), AverageHeight * (CurrentRow-1), Child.DesiredSize.Width, Child.DesiredSize.Height);

    Child.Arrange (FinalRect);

    }

    return new Size (FinalSize.Width, TotalHeight / ColumnCount);

    }

     

    }

    <ListBox x:Name="Test" Width="400" >

     <ListBox.ItemsPanel>

      <ItemsPanelTemplate>

       <test:TestPanel ColumnCount="3" />

      </ItemsPanelTemplate>

     </ListBox.ItemsPanel>

     <ListBox.ItemTemplate>

      <DataTemplate>

       <CheckBox IsChecked="{Binding Indicator}" Content="{Binding Name}" />

      </DataTemplate>

     </ListBox.ItemTemplate>

    </ListBox>

     

     

    Sunday, October 12, 2008 5:43 PM