WPF Wrappanel 很好地对齐了文本块和文本框
WPF Wrappanel nicely aligned Textblocks and Textboxes
几个小时以来,我一直在绞尽脑汁想弄清楚如何让我的文本块和文本框在 Wrappanel 中对齐。我已经尝试了所有我能在 Whosebug 上找到的东西,但事实是在我的第一个 WPF 应用程序中,我很难弄清楚。
此 post 中详细描述了我想要实现的目标,但我无法使用此处概述的步骤使其工作:http://badecho.com/2012/07/wpf-grid-like-wrappanels/
这是我目前的情况:
<TabControl HorizontalAlignment="Left"
Margin="10,150,0,10"
VerticalAlignment="Top">
<TabItem Header="Repairs">
<Grid Margin="0,0,10,0">
<WrapPanel Grid.IsSharedSizeScope="True" Orientation="Horizontal" Margin="0,10,10,10">
<TextBlock TextWrapping="WrapWithOverflow" Margin="20, 5, 0, 20">
Regular Paid Hours
</TextBlock>
<TextBox Margin="20, 0, 10, 20" Width="45"></TextBox>
<TextBlock TextWrapping="WrapWithOverflow" Margin="20, 5, 0, 20">
Overtime Hours
</TextBlock>
<TextBox Margin="20, 0, 10, 20" Width="45"></TextBox>
<TextBlock TextWrapping="WrapWithOverflow" Margin="20, 5, 0, 20">
Repair Labor
</TextBlock>
<TextBox Margin="20, 0, 10, 20" Width="45"></TextBox>\
<!-- There are a lot more -->
</WrapPanel>
<DataGrid AutoGenerateColumns="False" ColumnHeaderStyle="{StaticResource lowCase}" Margin="20,180,10,70" Name="dtGrid" HorizontalAlignment="Left" CanUserResizeRows="False" ItemsSource="{Binding}" VerticalAlignment="Top" GridLinesVisibility="All">
<DataGrid.Columns>
<DataGridTextColumn Binding="{Binding Path=Location}" Header="Location"/>
<DataGridTextColumn Binding="{Binding Path=Date, StringFormat ='MM-dd-yy'}" Header="Date"/>
<DataGridTextColumn Binding="{Binding Path=RegularPaidHours}" Header="Regular Repair Hours"/>
</DataGrid.Columns>
</DataGrid>
</Grid>
我想要实现的目标:调整 window 大小时,文本框应对齐,数据网格应向下移动以适合所有文本块和文本框。我错过了什么?
有人可以给我提供一个防哑解决方案吗?如果能提供简单的修复方法,我将不胜感激。
这是一种使用隐式样式和 HeaderedContentControls
的方法。您可以在 ControlTemplate
中设置页边距、宽度等。我把它留得很简单。 "InputCol" 单元格将默认水平拉伸其内容,但您可以在示例中看到如何针对特定控件取消它。容器上的 "SharedSizeGroup" 和 "IsSharedSizeScope" 是使所有标签具有相同宽度但不超过所需宽度的魔法。
<Window.Resources>
<Style TargetType="WrapPanel" x:Key="WrapForm">
<Setter Property="Orientation" Value="Horizontal" />
<Setter Property="Grid.IsSharedSizeScope" Value="True" />
<Style.Resources>
<!-- Implicit style for all HeaderedContentControls -->
<Style TargetType="HeaderedContentControl">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="HeaderedContentControl">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto" SharedSizeGroup="LabelCol" />
<ColumnDefinition Width="120" SharedSizeGroup="InputCol" />
</Grid.ColumnDefinitions>
<Label
VerticalContentAlignment="Top"
Grid.Column="0"
Content="{TemplateBinding Header}"
/>
<ContentControl
VerticalContentAlignment="Top"
Grid.Column="1"
Content="{TemplateBinding Content}"
/>
</Grid>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</Style.Resources>
</Style>
</Window.Resources>
<Grid>
<WrapPanel Style="{StaticResource WrapForm}">
<HeaderedContentControl Header="Regular Paid Hours">
<TextBox />
</HeaderedContentControl>
<HeaderedContentControl Header="Overtime Hours">
<TextBox />
</HeaderedContentControl>
<HeaderedContentControl Header="Repair Labor">
<ComboBox HorizontalAlignment="Left" />
</HeaderedContentControl>
<HeaderedContentControl Header="This One Has Two">
<StackPanel Orientation="Vertical">
<CheckBox>One Thing</CheckBox>
<CheckBox>Or Another</CheckBox>
</StackPanel>
</HeaderedContentControl>
</WrapPanel>
</Grid>
更新
简单的两行网格布局:
<Grid>
<Grid.RowDefinitions>
<!--
This 2* + 1* means "divide the grid vertically into three equal parts,
and give two of them to row zero and one of them to row one".
You could give them both Height="*" and it'll be divided evenly, or
make one of them Height="Auto" and it'll get the height it takes up,
while the other one will get all the remainder.
-->
<RowDefinition Height="2*" />
<RowDefinition Height="1*" />
</Grid.RowDefinitions>
<ScrollViewer
Grid.Row="0"
>
<WrapPanel
Style="{StaticResource WrapForm}"
>
<HeaderedContentControl Header="Regular Paid Hours">
<TextBox />
</HeaderedContentControl>
<HeaderedContentControl Header="Overtime Hours">
<TextBox />
</HeaderedContentControl>
<HeaderedContentControl Header="Repair Labor">
<ComboBox HorizontalAlignment="Left" />
</HeaderedContentControl>
<HeaderedContentControl Header="This One Has Two">
<StackPanel Orientation="Vertical">
<CheckBox>One Thing</CheckBox>
<CheckBox>Or Another</CheckBox>
</StackPanel>
</HeaderedContentControl>
</WrapPanel>
</ScrollViewer>
<DataGrid
Grid.Row="0">
<!-- stuff -->
</DataGrid>
</Grid>
这里的网格是Window中的主网格。可能需要一些技巧才能按照您想要的方式获得它。
几个小时以来,我一直在绞尽脑汁想弄清楚如何让我的文本块和文本框在 Wrappanel 中对齐。我已经尝试了所有我能在 Whosebug 上找到的东西,但事实是在我的第一个 WPF 应用程序中,我很难弄清楚。
此 post 中详细描述了我想要实现的目标,但我无法使用此处概述的步骤使其工作:http://badecho.com/2012/07/wpf-grid-like-wrappanels/
这是我目前的情况:
<TabControl HorizontalAlignment="Left"
Margin="10,150,0,10"
VerticalAlignment="Top">
<TabItem Header="Repairs">
<Grid Margin="0,0,10,0">
<WrapPanel Grid.IsSharedSizeScope="True" Orientation="Horizontal" Margin="0,10,10,10">
<TextBlock TextWrapping="WrapWithOverflow" Margin="20, 5, 0, 20">
Regular Paid Hours
</TextBlock>
<TextBox Margin="20, 0, 10, 20" Width="45"></TextBox>
<TextBlock TextWrapping="WrapWithOverflow" Margin="20, 5, 0, 20">
Overtime Hours
</TextBlock>
<TextBox Margin="20, 0, 10, 20" Width="45"></TextBox>
<TextBlock TextWrapping="WrapWithOverflow" Margin="20, 5, 0, 20">
Repair Labor
</TextBlock>
<TextBox Margin="20, 0, 10, 20" Width="45"></TextBox>\
<!-- There are a lot more -->
</WrapPanel>
<DataGrid AutoGenerateColumns="False" ColumnHeaderStyle="{StaticResource lowCase}" Margin="20,180,10,70" Name="dtGrid" HorizontalAlignment="Left" CanUserResizeRows="False" ItemsSource="{Binding}" VerticalAlignment="Top" GridLinesVisibility="All">
<DataGrid.Columns>
<DataGridTextColumn Binding="{Binding Path=Location}" Header="Location"/>
<DataGridTextColumn Binding="{Binding Path=Date, StringFormat ='MM-dd-yy'}" Header="Date"/>
<DataGridTextColumn Binding="{Binding Path=RegularPaidHours}" Header="Regular Repair Hours"/>
</DataGrid.Columns>
</DataGrid>
</Grid>
我想要实现的目标:调整 window 大小时,文本框应对齐,数据网格应向下移动以适合所有文本块和文本框。我错过了什么?
有人可以给我提供一个防哑解决方案吗?如果能提供简单的修复方法,我将不胜感激。
这是一种使用隐式样式和 HeaderedContentControls
的方法。您可以在 ControlTemplate
中设置页边距、宽度等。我把它留得很简单。 "InputCol" 单元格将默认水平拉伸其内容,但您可以在示例中看到如何针对特定控件取消它。容器上的 "SharedSizeGroup" 和 "IsSharedSizeScope" 是使所有标签具有相同宽度但不超过所需宽度的魔法。
<Window.Resources>
<Style TargetType="WrapPanel" x:Key="WrapForm">
<Setter Property="Orientation" Value="Horizontal" />
<Setter Property="Grid.IsSharedSizeScope" Value="True" />
<Style.Resources>
<!-- Implicit style for all HeaderedContentControls -->
<Style TargetType="HeaderedContentControl">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="HeaderedContentControl">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto" SharedSizeGroup="LabelCol" />
<ColumnDefinition Width="120" SharedSizeGroup="InputCol" />
</Grid.ColumnDefinitions>
<Label
VerticalContentAlignment="Top"
Grid.Column="0"
Content="{TemplateBinding Header}"
/>
<ContentControl
VerticalContentAlignment="Top"
Grid.Column="1"
Content="{TemplateBinding Content}"
/>
</Grid>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</Style.Resources>
</Style>
</Window.Resources>
<Grid>
<WrapPanel Style="{StaticResource WrapForm}">
<HeaderedContentControl Header="Regular Paid Hours">
<TextBox />
</HeaderedContentControl>
<HeaderedContentControl Header="Overtime Hours">
<TextBox />
</HeaderedContentControl>
<HeaderedContentControl Header="Repair Labor">
<ComboBox HorizontalAlignment="Left" />
</HeaderedContentControl>
<HeaderedContentControl Header="This One Has Two">
<StackPanel Orientation="Vertical">
<CheckBox>One Thing</CheckBox>
<CheckBox>Or Another</CheckBox>
</StackPanel>
</HeaderedContentControl>
</WrapPanel>
</Grid>
更新
简单的两行网格布局:
<Grid>
<Grid.RowDefinitions>
<!--
This 2* + 1* means "divide the grid vertically into three equal parts,
and give two of them to row zero and one of them to row one".
You could give them both Height="*" and it'll be divided evenly, or
make one of them Height="Auto" and it'll get the height it takes up,
while the other one will get all the remainder.
-->
<RowDefinition Height="2*" />
<RowDefinition Height="1*" />
</Grid.RowDefinitions>
<ScrollViewer
Grid.Row="0"
>
<WrapPanel
Style="{StaticResource WrapForm}"
>
<HeaderedContentControl Header="Regular Paid Hours">
<TextBox />
</HeaderedContentControl>
<HeaderedContentControl Header="Overtime Hours">
<TextBox />
</HeaderedContentControl>
<HeaderedContentControl Header="Repair Labor">
<ComboBox HorizontalAlignment="Left" />
</HeaderedContentControl>
<HeaderedContentControl Header="This One Has Two">
<StackPanel Orientation="Vertical">
<CheckBox>One Thing</CheckBox>
<CheckBox>Or Another</CheckBox>
</StackPanel>
</HeaderedContentControl>
</WrapPanel>
</ScrollViewer>
<DataGrid
Grid.Row="0">
<!-- stuff -->
</DataGrid>
</Grid>
这里的网格是Window中的主网格。可能需要一些技巧才能按照您想要的方式获得它。