UniformGrid 的第 属性 行

Rows Property of UniformGrid

我是 WPF 的新手,正在尝试了解如何使用 UniformGridhttps://docs.microsoft.com/en-us/windows/communitytoolkit/controls/uniformgrid

If no value for Rows and Columns are provided, the UniformGrid will create a square layout based on the total number of visible items. If a fixed size is provided for Rows and Columns then additional children that can't fit in the number of cells provided won't be displayed.

根据这篇文章,我想如果我将 10 个项目的集合绑定到一个统一的网格并指定 1 行和 3 列,那么它只会显示 3 个项目,其他 7 个将被截断。

但是,我已经构建了一个示例应用程序,并且我的集合中有 1 行、3 列和 10 个项目,我显示了 4 行。这是我的示例应用程序:

<Window x:Class="UniformGridTest.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:local="clr-namespace:UniformGridTest"
        mc:Ignorable="d"
        Title="MainWindow" Height="450" Width="800"
        Name="MyMainWindow">
    <ItemsControl ItemsSource="{Binding ActiveList}" Background="Black">
        <ItemsControl.ItemsPanel>
            <ItemsPanelTemplate>
                <UniformGrid HorizontalAlignment="Stretch" VerticalAlignment="Center" Rows="1" Columns="3"/>
            </ItemsPanelTemplate>
        </ItemsControl.ItemsPanel>
        <ItemsControl.ItemTemplate>
            <DataTemplate>
                <Button Content="{Binding ItemDescription}" Background="Black" Foreground="White"/>
            </DataTemplate>
        </ItemsControl.ItemTemplate>
    </ItemsControl>
</Window>
using System.Collections.ObjectModel;
using System.ComponentModel;
using System.Windows;

namespace UniformGridTest
{
    /// <summary>
    /// Interaction logic for MainWindow.xaml
    /// </summary>
    public partial class MainWindow : Window
    {
        private readonly PlatformSelectorViewModel platformSelectorViewModel = new PlatformSelectorViewModel();
        public MainWindow()
        {
            InitializeComponent();
            DataContext = platformSelectorViewModel;
        }
    }

    public class PlatformSelectorViewModel
    {
        public ObservableCollection<SelectorItem> ActiveList { get; }

        public PlatformSelectorViewModel()
        {
            ActiveList = new ObservableCollection<SelectorItem>();
            ActiveList.Add(new SelectorItem() { ItemDescription = "Super Nintendo Entertainment System" });
            ActiveList.Add(new SelectorItem() { ItemDescription = "Nintendo Entertainment System" });
            ActiveList.Add(new SelectorItem() { ItemDescription = "Sega Genesis" });
            ActiveList.Add(new SelectorItem() { ItemDescription = "Sega CD" });
            ActiveList.Add(new SelectorItem() { ItemDescription = "Turbo Grafx 16" });
            ActiveList.Add(new SelectorItem() { ItemDescription = "Nintendo Gamecube" });
            ActiveList.Add(new SelectorItem() { ItemDescription = "Nintendo Wii" });
            ActiveList.Add(new SelectorItem() { ItemDescription = "Sony Playstation" });
            ActiveList.Add(new SelectorItem() { ItemDescription = "Nintendo PSP" });
            ActiveList.Add(new SelectorItem() { ItemDescription = "Nintendo Playstation 2" });
            ActiveList.Add(new SelectorItem() { ItemDescription = "Arcade" });
        }
    }

    public class SelectorItem : INotifyPropertyChanged
    {
        private string itemDescription;
        public string ItemDescription
        {
            get { return itemDescription; }
            set
            {
                itemDescription = value;
                PropertyChanged(this, new PropertyChangedEventArgs("ItemDescription"));
            }
        }

        private bool isSelected;
        public bool IsSelected
        {
            get { return isSelected; }
            set
            {
                isSelected = value;
                PropertyChanged(this, new PropertyChangedEventArgs("IsSelected"));
            }
        }

        public event PropertyChangedEventHandler PropertyChanged = delegate { };
    }
}

结果:

根据 UniformGrid 上的文档,我预计我会得到 1 行,其中 3 个项目统一布局,而其他 7 个项目不会显示。是我误解了文档还是我做错了什么导致显示额外的行?

首先,您引用了错误的文档,您的文档适用于 UWP,而不是 WPF。

行为应该相同,但 WPF 参考文档中并未明确说明。然而,似乎有一个问题源于将 VerticalAlignment 设置为 Center,并且与 ItemsControl 无关,对于孤立的 UniformGrid 也是一样的。

只要 UniformGrid 包含的项目数超过它可以显示的最大项目数 (Rows x Columns) VerticalAlignment 设置为默认值 Stretch 以外的任何其他值时,无论行数如何,都会显示所有项目,但会考虑列数。

您可以删除 VerticalAlignment 并尝试通过对齐 ItemsControl 以符合您的原始意图来补偿它。

<ItemsPanelTemplate>
   <UniformGrid HorizontalAlignment="Stretch" Rows="1" Columns="3"/>
</ItemsPanelTemplate>