2

我将项目控件绑定到数据源并使用网格作为我的项目主机。我希望让这些项目将自己定位到网格中的正确单元格中(我可以这样做),并且还将它们自己堆叠起来,这样它们就不会全部重叠(我不知道如何将这些项目插入到stackpanel 或网格中的其他面板)。

这是两个类的 .cs 文件:

   public class listofdata
    {
        public List<data> stuff { get; set; }
        public listofdata()
        {
            stuff = new List<data>();
            stuff.Add(new data(0, 0, "zeroa"));
            stuff.Add(new data(0, 0, "zerob"));
            stuff.Add(new data(1, 0, "onea"));
            stuff.Add(new data(1, 0, "oneb"));
            stuff.Add(new data(1, 1, "twoa"));
            stuff.Add(new data(1, 1, "twob"));
        }
    }

    public class data
    {
        public int x { set; get; }
        public int y { set; get; }
        public string text { get; set; }
        public data(int x, int y, string text)
        {
            this.x = x;
            this.y = y;
            this.text = text;
        }
    }
}

这是我的 XAML

   <Window x:Class="GridTester.MainWindow"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"

    xmlns:src="clr-namespace:GridTester"
    xmlns:sys="clr-namespace:System;assembly=mscorlib"

    Title="MainWindow" >
<Window.Resources>
    <DataTemplate DataType="{x:Type src:data}">
        <Button Content="{Binding text}"/>
    </DataTemplate>
    <src:listofdata x:Key="MyDataSource"> </src:listofdata>


</Window.Resources>
<ListBox Name="Main" ItemsSource="{Binding Source={StaticResource MyDataSource},Path=stuff}">
    <ListBox.ItemsPanel>
        <ItemsPanelTemplate>
            <Grid Name="MyGrid">
                <Grid.ColumnDefinitions>
                    <ColumnDefinition/>

                    <ColumnDefinition/>
                </Grid.ColumnDefinitions>
                <Grid.RowDefinitions>
                    <RowDefinition />
                    <RowDefinition />
                </Grid.RowDefinitions>
            </Grid>
        </ItemsPanelTemplate>
    </ListBox.ItemsPanel>

    <ListBox.ItemContainerStyle>
        <Style>
            <Setter Property="Grid.Column" Value="{Binding x}"/>
            <Setter Property="Grid.Row" Value="{Binding y}"/>
        </Style>
    </ListBox.ItemContainerStyle> 

</ListBox>


</Window>

我的问题是所有以'a'结尾的按钮都在以b结尾的按钮下。我看不到如何使用 XAML 将项目插入动态创建的堆栈面板

我试图创建一个从 Grid 派生的类,考虑拦截添加子项以自己添加堆栈面板,然后将子项从网格移动到堆栈面板,但尝试在 itemshost 中操作子项会导致抛出异常。

最终我只希望我的数据源中的项目能够绑定到网格中的“单元格”,如果多个项目绑定到同一个单元格,我希望它们堆叠。

4

2 回答 2

1

这是使用 nmclean 提示的解决方案(非常感谢) 本节建立了用于在网格周围分布元素的分组。

<CollectionViewSource Source="{Binding Source={StaticResource MyDataSource}}" x:Key="cvs">


        <CollectionViewSource.GroupDescriptions>
            <PropertyGroupDescription PropertyName="ordinal"/>


        </CollectionViewSource.GroupDescriptions>

    </CollectionViewSource>

此部分是绑定到 collectionviewsource 中数据的主列表框,containerstyle 包含将 groupitem 放入网格中正确单元格的绑定。网格位于 groupstyle.panel

  <ListBox  ItemsSource ="{Binding Source={StaticResource cvs}}"   >
    <ListBox.GroupStyle>
        <GroupStyle>
            <GroupStyle.ContainerStyle>
                <Style TargetType="{x:Type GroupItem}">
                    <Setter Property="Grid.Row" Value="{Binding Items[0].y,diag:PresentationTraceSources.TraceLevel=High}" />
                    <Setter Property="Grid.Column" Value="{Binding Items[0].x,diag:PresentationTraceSources.TraceLevel=High}" />


                </Style>
            </GroupStyle.ContainerStyle>
            <GroupStyle.Panel>
                <ItemsPanelTemplate>
                    <Grid>
                        <Grid.RowDefinitions>
                            <RowDefinition></RowDefinition>
                            <RowDefinition></RowDefinition>
                            <RowDefinition></RowDefinition>
                        </Grid.RowDefinitions>
                        <Grid.ColumnDefinitions>
                            <ColumnDefinition></ColumnDefinition>
                            <ColumnDefinition></ColumnDefinition>
                            <ColumnDefinition></ColumnDefinition>
                        </Grid.ColumnDefinitions>
                    </Grid>
                </ItemsPanelTemplate>
            </GroupStyle.Panel>
        </GroupStyle>
    </ListBox.GroupStyle>

以下是您需要时的整体解决方案:

<Window x:Class="GridTester.Window1"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:diag="clr-namespace:System.Diagnostics;assembly=WindowsBase"
        xmlns:src="clr-namespace:GridTester"
        xmlns:sys="clr-namespace:System;assembly=mscorlib"

        Title="Window1" Height="300" Width="300" Name="TOPWindow">
    <Window.Resources>

        <DataTemplate DataType="{x:Type src:data}">
            <Button Content="{Binding text}"/>
        </DataTemplate>
        <src:listofdata x:Key="MyDataSource"></src:listofdata>
        <CollectionViewSource Source="{Binding Source={StaticResource MyDataSource}}" x:Key="cvs">


            <CollectionViewSource.GroupDescriptions>
                <PropertyGroupDescription PropertyName="ordinal"/>


            </CollectionViewSource.GroupDescriptions>

        </CollectionViewSource>


    </Window.Resources>



    <ListBox  ItemsSource ="{Binding Source={StaticResource cvs}}"   >
        <ListBox.GroupStyle>
            <GroupStyle>
                <GroupStyle.ContainerStyle>
                    <Style TargetType="{x:Type GroupItem}">
                        <Setter Property="Grid.Row" Value="{Binding Items[0].y,diag:PresentationTraceSources.TraceLevel=High}" />
                        <Setter Property="Grid.Column" Value="{Binding Items[0].x,diag:PresentationTraceSources.TraceLevel=High}" />


                    </Style>
                </GroupStyle.ContainerStyle>
                <GroupStyle.Panel>
                    <ItemsPanelTemplate>
                        <Grid>
                            <Grid.RowDefinitions>
                                <RowDefinition></RowDefinition>
                                <RowDefinition></RowDefinition>
                                <RowDefinition></RowDefinition>
                            </Grid.RowDefinitions>
                            <Grid.ColumnDefinitions>
                                <ColumnDefinition></ColumnDefinition>
                                <ColumnDefinition></ColumnDefinition>
                                <ColumnDefinition></ColumnDefinition>
                            </Grid.ColumnDefinitions>
                        </Grid>
                    </ItemsPanelTemplate>
                </GroupStyle.Panel>
            </GroupStyle>
        </ListBox.GroupStyle>


    </ListBox>



</Window>

代码文件现在看起来像这样:

  public class listofdata : List<data>
{

    public listofdata()
    {

        Add(new data(0, 0, "zeroa"));
        Add(new data(0, 0, "zerob"));
        Add(new data(1, 0, "onea"));
        Add(new data(1, 0, "oneb"));
        Add(new data(1, 1, "twoa"));
        Add(new data(1, 1, "twob"));


    }

}

public class data
{
    public int x { set; get; }
    public int y { set; get; }
    public int ordinal { get { return x * 1000 + y; } }
    public string text { get; set; }
    public data(int x, int y, string text)
    {
        this.x = x;
        this.y = y;
        this.text = text;
    }

}
于 2013-07-27T18:03:19.373 回答
1

您可以像 HighCore 建议的那样在数据级别执行此操作,但由于当前数据结构已经包含必要的信息,因此 ItemsControl 应该可以处理它。考虑向 ListBox 的项目集合添加组描述,并使用Panel为 StackPanel的GroupStyle 。

于 2013-07-25T17:00:03.813 回答