Search code examples
.netwpfxaml.net-4.5wrappanel

Stretch WrapPanel items


I have WrapPanel and very similar items within it. Maybe WrapPanel is a wrong container, just describing what I have.

I want all items have equal width; minimum width of 120. Also, I want items to stretch, that is the point.

If WrapPanel width is 150 (less than 2*minimum) there will be one column and items' width will be 150.

If WrapPanel width is 350 (less than 3*minimum) there will be two columns and items' width will be 175 (350/2).

If WrapPanel width is 370 (less than 4*minimum) there will be three columns and items' width will be 123 (370/3). It can be also two items of 123 and one of 124, does not really matter.

The question is how can I get this behavior?


Solution

  • C# code:

    public MainWindow()
    {
        DataContext = this;
        SomeList.Add(new SomeType());
        SomeList.Add(new SomeType());
        SomeList.Add(new SomeType());
        SomeList.Add(new SomeType());
        SomeList.Add(new SomeType());
        InitializeComponent();
    }
    //SomeList Observable Collection
    private ObservableCollection<SomeType> _someList =
        new ObservableCollection<SomeType>();
    public ObservableCollection<SomeType> SomeList { get { return _someList; } }
    private void UniformGrid_SizeChanged(object sender, SizeChangedEventArgs e)
    {
        var grid = sender as UniformGrid;
        if (grid.ActualWidth > 370) grid.Columns = 3;
        else if (grid.ActualWidth > 150) grid.Columns = 2;
        else grid.Columns = 1;
    }
    public class SomeType : DependencyObject
    {
        //Title Dependency Property
        public string Title
        {
            get { return (string)GetValue(TitleProperty); }
            set { SetValue(TitleProperty, value); }
        }
        public static readonly DependencyProperty TitleProperty =
            DependencyProperty.Register("Title", typeof(string), typeof(SomeType),
            new UIPropertyMetadata("unset yet"));
    }
    

    XAML code:

    <Window.Resources>
        <DataTemplate x:Key="SomeTemplate" DataType="{x:Type local:SomeType}">
            <Border BorderBrush="Black" BorderThickness="2" CornerRadius="4">
                <TextBlock Text="{Binding Title}"/>
            </Border>
        </DataTemplate>
    </Window.Resources>
    <ItemsControl
        ItemsSource="{Binding SomeList}"
        ItemTemplate="{StaticResource SomeTemplate}">
        <ItemsControl.ItemsPanel>
            <ItemsPanelTemplate>
                <UniformGrid SizeChanged="UniformGrid_SizeChanged"/>
            </ItemsPanelTemplate>
        </ItemsControl.ItemsPanel>
    </ItemsControl>