WPF Datagrid行拉伸以填充没有滚动条的空间

时间:2016-06-15 22:28:27

标签: wpf xaml blend

每当Window处于任何大小时,我都无法让我的DataGrid将行拉伸以填充所有可用空间。在这种情况下,它应该填充父网格第二行(7 *)中的所有空格。 DataGrid将始终具有20行和2列。我从不想要显示任何滚动条。

我希望DataGrid看起来像这样:

Ideal

但是,如果窗口太短,则会截断项目:

Truncated

如果窗口太高,数据网格底部会出现一个丑陋的灰色区域:

Grey at bottom

这是Xaml:

<UserControl
    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:ignore="http://www.galasoft.ch/ignore"
    xmlns:viewModel="clr-namespace:WMT.ViewModel"
    xmlns:view="clr-namespace:WMT.View"
    xmlns:Design="clr-namespace:WMT.Design"
    xmlns:res="clr-namespace:WMT.Resources"
    xmlns:local="clr-namespace:WMT"
    xmlns:i="http://schemas.microsoft.com/expression/2010/interactivity"
    xmlns:ei="http://schemas.microsoft.com/expression/2010/interactions"
    xmlns:Custom="http://www.galasoft.ch/mvvmlight"
    xmlns:debug="debug-mode"
    xmlns:System="clr-namespace:System;assembly=mscorlib"
    xmlns:Converters="clr-namespace:GTP.Contracts.Converters;assembly=GTP.Contracts"
    xmlns:Behaviours="clr-namespace:GTP.Contracts.Behaviours;assembly=GTP.Contracts"
    x:Class="WMT.View.FRView"
    mc:Ignorable="d mc"
    d:DesignWidth="706"
    d:DesignHeight="554" 
    d:DataContext="{d:DesignInstance {x:Type Design:DesignFRViewModel}, IsDesignTimeCreatable=True}" ScrollViewer.VerticalScrollBarVisibility="Disabled"
    >
<UserControl.Resources>
    <ResourceDictionary>
        <ResourceDictionary.MergedDictionaries>
            <ResourceDictionary Source="pack://application:,,,/WMT;component/Styles.xaml"/>
        </ResourceDictionary.MergedDictionaries>
        <Converters:NegateConverter x:Key="NegateConverter"/>
        <System:Double x:Key="StandardWidth">240</System:Double>
        <Thickness x:Key="StandardMargin">0,0,10,0</Thickness>
    </ResourceDictionary>
</UserControl.Resources>
<UserControl.Background>
    <ImageBrush ImageSource="/WMT;component/Images/cloud.bmp"/>
</UserControl.Background>

<Grid ShowGridLines="True">
    <Grid.ColumnDefinitions>
        <ColumnDefinition/>
        <ColumnDefinition/>
    </Grid.ColumnDefinitions>
    <Grid.RowDefinitions>
        <RowDefinition Height="0.5*"/>
        <RowDefinition Height="7*"/>
        <RowDefinition Height="2.5*"/>
    </Grid.RowDefinitions>
    <DataGrid Grid.Row="1" 
              ItemsSource="{Binding WmtResult.Responses}" 
              AutoGenerateColumns="False" 
              CanUserReorderColumns="False" 
              CanUserResizeColumns="False" 
              CanUserSortColumns="False" 
              GridLinesVisibility="None" 
              CanUserAddRows="False" 
              CanUserDeleteRows="False" 
              CanUserResizeRows="False" 
              RowHeaderWidth="0" 
              HorizontalContentAlignment="Stretch" 
              VerticalContentAlignment="Stretch" 
              HorizontalScrollBarVisibility="Disabled" 
              VerticalScrollBarVisibility="Disabled">
        <DataGrid.Columns>
            <DataGridTextColumn Binding="{Binding IRPrompt.Item}" 
                                ClipboardContentBinding="{x:Null}"
                                Width="3*" 
                                Header="Word"/>
            <DataGridTextColumn Binding="{Binding FRPrompt}" 
                                ClipboardContentBinding="{x:Null}" 
                                Width="*" 
                                Header="Count"/>
        </DataGrid.Columns>
    </DataGrid>
</Grid>

我尝试过ListView而不是DataGrid,但遇到了类似的问题。我需要在某个地方使用Viewbox吗?如果您需要更多信息,请与我们联系。感谢。

修改

我正在尝试Ryan Flohr建议将DataGrid放在Viewbox中。这解决了截断问题和DataGrid问题下面的灰色区域。 DataGrid正确地垂直填充空间,但它不会水平填充空间。

这是更新后的xaml:

<UserControl
    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:ignore="http://www.galasoft.ch/ignore"
    xmlns:viewModel="clr-namespace:WMT.ViewModel"
    xmlns:view="clr-namespace:WMT.View"
    xmlns:Design="clr-namespace:WMT.Design"
    xmlns:res="clr-namespace:WMT.Resources"
    xmlns:local="clr-namespace:WMT"
    xmlns:i="http://schemas.microsoft.com/expression/2010/interactivity"
    xmlns:ei="http://schemas.microsoft.com/expression/2010/interactions"
    xmlns:Custom="http://www.galasoft.ch/mvvmlight"
    xmlns:debug="debug-mode"
    xmlns:System="clr-namespace:System;assembly=mscorlib"
    xmlns:Converters="clr-namespace:GTP.Contracts.Converters;assembly=GTP.Contracts"
    xmlns:Behaviours="clr-namespace:GTP.Contracts.Behaviours;assembly=GTP.Contracts"
    x:Class="WMT.View.FRView"
    mc:Ignorable="d mc"
    d:DesignWidth="754"
    d:DesignHeight="685" 
    d:DataContext="{d:DesignInstance {x:Type Design:DesignFRViewModel}, IsDesignTimeCreatable=True}" ScrollViewer.VerticalScrollBarVisibility="Disabled"
    >
<UserControl.Resources>
    <ResourceDictionary>
        <ResourceDictionary.MergedDictionaries>
            <ResourceDictionary Source="pack://application:,,,/WMT;component/Styles.xaml"/>
        </ResourceDictionary.MergedDictionaries>
        <Converters:NegateConverter x:Key="NegateConverter"/>
        <System:Double x:Key="StandardWidth">240</System:Double>
        <Thickness x:Key="StandardMargin">0,0,10,0</Thickness>
    </ResourceDictionary>
</UserControl.Resources>
<UserControl.Background>
    <ImageBrush ImageSource="/WMT;component/Images/cloud.bmp"/>
</UserControl.Background>
<Grid>
    <Grid.ColumnDefinitions>
        <ColumnDefinition/>
        <ColumnDefinition/>
    </Grid.ColumnDefinitions>
    <Grid.RowDefinitions>
        <RowDefinition Height="0.5*"/>
        <RowDefinition Height="7*"/>
        <RowDefinition Height="2.5*"/>
    </Grid.RowDefinitions>
    <Viewbox Grid.Row="1">
        <DataGrid Grid.Row="1" 
                  ItemsSource="{Binding WmtResult.Responses}" 
                  AutoGenerateColumns="False" 
                  CanUserReorderColumns="False" 
                  CanUserResizeColumns="False" 
                  CanUserSortColumns="False" 
                  GridLinesVisibility="None" 
                  CanUserAddRows="False" 
                  CanUserDeleteRows="False" 
                  CanUserResizeRows="False" 
                  RowHeaderWidth="0" 
                  VerticalContentAlignment="Stretch" 
                  HorizontalScrollBarVisibility="Disabled" 
                  VerticalScrollBarVisibility="Disabled" HorizontalContentAlignment="Stretch">
            <DataGrid.Columns>
                <DataGridTextColumn Binding="{Binding IRPrompt.Item}" 
                                    ClipboardContentBinding="{x:Null}" 
                                    Header="Word"
                                    >
                    <!--<DataGridTextColumn.CellStyle>
                        <Style TargetType="{x:Type DataGridCell}">
                            <Setter Property="Margin" Value="0,0,190,0" />
                        </Style>
                    </DataGridTextColumn.CellStyle>-->
                </DataGridTextColumn>
                <DataGridTextColumn Binding="{Binding FRPrompt}" 
                                    ClipboardContentBinding="{x:Null}" 
                                    Header="Count">
                    <!--<DataGridTextColumn.CellStyle>
                        <Style TargetType="{x:Type DataGridCell}">
                            <Setter Property="Margin" Value="0,0,60,0" />
                        </Style>
                    </DataGridTextColumn.CellStyle>-->
                </DataGridTextColumn>
            </DataGrid.Columns>
        </DataGrid>
    </Viewbox>

</Grid>

以下是截图:

Viewbox No Margin

我尝试使用DataGrid的Horizo​​ntalAlignment和Horizo​​ntalContentAlignment,但没有运气。然后我更改了列的边距(请参阅xaml的注释部分),但只有在窗口具有特定大小时才能获得适当的边距。这是我将边距设置为精确值的屏幕截图(请参阅xaml中注释的CellStyle部分):

ViewboxMarginTooSkinny ViewboxMarginTooShort

我想我可以使用ValueConverter将Margin绑定到Viewbox的实际宽度的百分比,但是这看起来很糟糕。

有没有办法用一些水平填充空间的布局控件替换DataGrid的内部StackPanel?第1列的宽度应为第2列的3倍。

2 个答案:

答案 0 :(得分:1)

如果您想要显示所有20行,即使窗口的大小太小,同时没有显示任何垂直滚动条,您也必须将DataGrid放在ViewBox中。这也将确保不会显示“丑陋的灰色”。

在DataGrid控件的内部,内容本身位于StackPanel内部,它将增长到内容本身所需的任何空间。 StackPanel位于ScrollViewer内部,因此如果内容对于Window太大,您可以滚动它。由于您已禁用滚动条功能,因此它实际上只是一个将继续增长的StackPanel。由于您已在Grid上设置了显式大小限制,因此DataGrid仅显示其大小允许的DataGrid部分,从而使内容看起来被截断。另一方面,如果网格比StackPanel中的内部内容大得多,则StackPanel会向网格调整大小,但其内容会停止。你看到的那种“丑陋”的灰色是控件的背景颜色。

答案 1 :(得分:1)

通过在Stregch设置为Fill的DataGrid周围使用Viewbox,我能够达到预期的效果。我还必须在DataGrid上设置高度和宽度,以便为窗口大小更改时保留纵横比。这是xaml:

<UserControl
    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:ignore="http://www.galasoft.ch/ignore"
    xmlns:viewModel="clr-namespace:WMT.ViewModel"
    xmlns:view="clr-namespace:WMT.View"
    xmlns:Design="clr-namespace:WMT.Design"
    xmlns:res="clr-namespace:WMT.Resources"
    xmlns:local="clr-namespace:WMT"
    xmlns:i="http://schemas.microsoft.com/expression/2010/interactivity"
    xmlns:ei="http://schemas.microsoft.com/expression/2010/interactions"
    xmlns:Custom="http://www.galasoft.ch/mvvmlight"
    xmlns:debug="debug-mode"
    xmlns:System="clr-namespace:System;assembly=mscorlib"
    xmlns:Converters="clr-namespace:GTP.Contracts.Converters;assembly=GTP.Contracts"
    xmlns:Behaviours="clr-namespace:GTP.Contracts.Behaviours;assembly=GTP.Contracts"
    x:Class="WMT.View.FRView"
    mc:Ignorable="d mc"
    d:DesignWidth="688"
    d:DesignHeight="554" 
    d:DataContext="{d:DesignInstance {x:Type Design:DesignFRViewModel}, IsDesignTimeCreatable=True}" ScrollViewer.VerticalScrollBarVisibility="Disabled"
    >
<UserControl.Resources>
    <ResourceDictionary>
        <ResourceDictionary.MergedDictionaries>
            <ResourceDictionary Source="pack://application:,,,/WMT;component/Styles.xaml"/>
        </ResourceDictionary.MergedDictionaries>
        <Converters:NegateConverter x:Key="NegateConverter"/>
        <System:Double x:Key="StandardWidth">240</System:Double>
        <Thickness x:Key="StandardMargin">0,0,10,0</Thickness>
    </ResourceDictionary>
</UserControl.Resources>
<UserControl.Background>
    <ImageBrush ImageSource="/WMT;component/Images/cloud.bmp"/>
</UserControl.Background>
<Grid>
    <Grid.ColumnDefinitions>
        <ColumnDefinition/>
        <ColumnDefinition/>
    </Grid.ColumnDefinitions>
    <Grid.RowDefinitions>
        <RowDefinition Height="0.5*"/>
        <RowDefinition Height="7*"/>
        <RowDefinition Height="2.5*"/>
    </Grid.RowDefinitions>
    <Viewbox Grid.Row="1" Stretch="Fill">
        <DataGrid Grid.Row="1"
                  Background="White"
                  ItemsSource="{Binding WmtResult.Responses}" 
                  AutoGenerateColumns="False" 
                  CanUserReorderColumns="False" 
                  CanUserResizeColumns="False" 
                  CanUserSortColumns="False" 
                  GridLinesVisibility="None" 
                  CanUserAddRows="False" 
                  CanUserDeleteRows="False" 
                  CanUserResizeRows="False" 
                  RowHeaderWidth="0" 
                  VerticalContentAlignment="Stretch" 
                  HorizontalScrollBarVisibility="Disabled" 
                  VerticalScrollBarVisibility="Disabled"
                  HorizontalContentAlignment="Stretch"
                  ColumnWidth="*"
                  IsReadOnly="True"
                  Height="385" Width="300">
            <DataGrid.Columns>
                <DataGridTextColumn Binding="{Binding IRPrompt.Item}" 
                                    ClipboardContentBinding="{x:Null}" 
                                    Header="Word"
                                    Width="2*"
                                    >
                </DataGridTextColumn>
                <DataGridTextColumn Binding="{Binding FRPrompt}" 
                                    ClipboardContentBinding="{x:Null}" 
                                    Header="Count"
                                    Width="*">
                  </DataGridTextColumn>
            </DataGrid.Columns>
        </DataGrid>
    </Viewbox>

</Grid>