WPF 中网格的隐式行定义

Posted

技术标签:

【中文标题】WPF 中网格的隐式行定义【英文标题】:Implicit RowDefinition for Grid in WPF 【发布时间】:2013-12-05 17:16:05 【问题描述】:

在 XAMl 中设计网格时,我们必须明确说明网格中将有多少行。

假设我们正在制作一个表单类型的应用程序。用户需要在其中填写其信息。有一个标签,然后有一个文本框。这会重复 10 次。

<Label Content="Name" />
<TextBox Text=Binding SomethingText" />

现在这将重复。现在我在这里定义一个网格。

1  <Grid>
2      <Grid.ColumnDefinitions>
3          <ColumnDefinition Width="60" />
4          <ColumnDefinition Width="*" />
5      </Grid.ColumnDefinitions>
6      <Grid.RowDefinitions>
7          <RowDefinition Height="Auto" />
8          <RowDefinition Height="Auto" />
9      </Grid.RowDefinitions>

10     <Label Grid.Row="0" Grid.Column="0" Content="Name" />
11     <TextBox Grid.Row="0" Grid.Column="1" Text="Binding SomethingText" />

12     <Label Grid.Row="1" Grid.Column="0" Content="Address" />
13     <TextBox Grid.Row="1" Grid.Column="1" Text="Binding SomeText" />
14  </Grid>

现在,如果我决定在网格中添加另一行。更改 Grid.Row="2" 将不起作用。它将与第 1 行重叠。要做到这一点,我需要在 Grid.RowDefinitions 中添加一个 RowDefinition。所以每次我都需要添加RowDefinition。

现在我的问题是,无论如何我不需要明确告诉 RowDefinitions。 WPF 自动使用最后一个 RowDefinition(第 8 行)。

所以我想要这样的输出。没有额外的行定义。有可能吗?

1  <Grid>
2      <Grid.ColumnDefinitions>
3          <ColumnDefinition Width="60" />
4          <ColumnDefinition Width="*" />
5      </Grid.ColumnDefinitions>
6      <Grid.RowDefinitions>
7          <RowDefinition Height="Auto" />
8          
9      </Grid.RowDefinitions>

10     <Label Grid.Row="0" Grid.Column="0" Content="Name" />
11     <TextBox Grid.Row="0" Grid.Column="1" Text="Binding SomethingText" />

12     <Label Grid.Row="1" Grid.Column="0" Content="Address" />
13     <TextBox Grid.Row="1" Grid.Column="1" Text="Binding SomeText" />

14     <Label Grid.Row="2" Grid.Column="0" Content="Address" />
15     <TextBox Grid.Row="2" Grid.Column="1" Text="Binding SomeText" />

16     <Label Grid.Row="3" Grid.Column="0" Content="Address" />
17     <TextBox Grid.Row="3" Grid.Column="1" Text="Binding SomeText" />
14  </Grid>

【问题讨论】:

由于您总是使用相同的控件,创建一个UserControl 并在DockPanelStackPanel 中重复它不是更好吗? 你这是什么意思? 我会给你一个答案。 【参考方案1】:

创建一个UserControl 并在StackPanelDockpanel 中重复它:

<UserControl ...>
    <Grid>
        <Grid.ColumnDefinitions>
            <ColumnDefinition Width="60" />
            <ColumnDefinition Width="*" />
        </Grid.ColumnDefinitions>

        <Label x:Name="label" Grid.Row="0" Grid.Column="0"/>
        <TextBox x:Name="textBox" Grid.Row="0" Grid.Column="1"/>
    </Grid>
</UserControl>

然后在您看来,要么使用DockPanel

<DockPanel>
    <c:YourUserControl DockPanel.Dock="Top" Label="Name" Value="Binding SomethingText"/>
    <c:YourUserControl DockPanel.Dock="Top" Label="Address" Value="Binding SomeText"/>
</DockPanel>

StackPanel

<StackPanel>
    <c:YourUserControl Label="Name" Value="Binding SomethingText"/>
    <c:YourUserControl Label="Address" Value="Binding SomeText"/>
</StackPanel>

【讨论】:

但如果您希望它适应内容大小,第一列的宽度可能会不同步。

以上是关于WPF 中网格的隐式行定义的主要内容,如果未能解决你的问题,请参考以下文章

基于B样条基函数的隐式曲面重建

如何创建可重用的 WPF 网格布局

带有自定义列的 WPF 数据网格绑定

在 WPF 中的网格中的单元格之间拖放自定义控件

具有默认内容的 WPF 自定义网格

如何在自定义 wpf 控件上绑定数据网格列的可见性?