无法检索实际宽度

Unable to retrieve actual Width

我只有一个列表视图

 <ListView Grid.Row="4" Grid.ColumnSpan="2"
           Margin="{Binding ElementName=BorderContainer, Path=Margin}"
            FontSize="{DynamicResource PlaceHolderFontSize}"
            ItemContainerStyle="{StaticResource ListItemContainerStyle}"
            Foreground="Black"
            >
            <ListView.View>
                <GridView ColumnHeaderContainerStyle="{StaticResource BorderlessHeader}">
                    <GridViewColumn Header="Last Backup Date/Time" HeaderTemplate="{StaticResource BlueHeader}" 
                                    Width="{Binding RelativeSource={RelativeSource Mode=FindAncestor, AncestorType=ListView}, Converter={StaticResource ColumnWidth},ConverterParameter=221}">
                        <GridViewColumn.CellTemplate>
                            <DataTemplate>
                                <TextBlock Text="{Binding Date}" ToolTip="{Binding Date}" FontSize="{DynamicResource ContentFontSize}" Style="{StaticResource GridColumText}"  />
                            </DataTemplate>
                        </GridViewColumn.CellTemplate>
                    </GridViewColumn>

如代码中所述,我正在使用转换器计算 header 宽度。在我的转换器中,我正在使用如下

  public object Convert(object value, Type target Type, object parameter, Culture Info culture)
    {
        ListView listview = value as ListView;
        double width = listview.ActualWidth;

但是 listview.actualwidth 结果总是给出“0”。为什么会这样?有什么想法吗?

如果你有例如 4 Columns,你可以尝试以下操作:

XAML

<ListView x:Name="listView">
    <ListView.View>
        <GridView>
            <GridViewColumn Width="{Binding ElementName=listView, Path=ActualWidth, Converter={StaticResource ColumnWidthConverter},ConverterParameter=4}">

            </GridViewColumn>
        </GridView>
    </ListView.View>
</ListView>

转换器

public class ColumnWidthConverter : IValueConverter
{
    public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
    {
        int columns;
        if (int.TryParse(parameter.ToString(), out columns))
        {
            double width;
            if (columns > 0 && double.TryParse(value.ToString(), out width))
            {
                return width / columns;
            }
        }
        return 100.0;
    }

    public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
    {
        return null;
    }
}

如果你想更动态,你可以写一个Behavior并附加到ListView。您可以在那里根据 Columns 计数动态计算值。

Why this is happening?

可能是因为 ListView 在调用 Convert 方法时实际宽度为 0。

any ideas?

您可以使用 MultiBindingIMultiValueConverter 绑定到 ListView 本身及其 ActualWidth 属性:

<GridViewColumn Header="Last Backup Date/Time" HeaderTemplate="{StaticResource BlueHeader}">
    <GridViewColumn.Width>
        <MultiBinding Converter="{StaticResource ColumnWidth}" ConverterParameter="221">
            <Binding Path="." RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=ListView}" />
            <Binding Path="ActualWidth" RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=ListView}" />
        </MultiBinding>
    </GridViewColumn.Width>
    <GridViewColumn.CellTemplate>
        <DataTemplate>
            <TextBlock Text="{Binding Date}" ToolTip="{Binding Date}" FontSize="{DynamicResource ContentFontSize}" Style="{StaticResource GridColumText}"  />
        </DataTemplate>
    </GridViewColumn.CellTemplate>
</GridViewColumn>

public class ColumnWidthConverter : IMultiValueConverter
{
    public object Convert(object[] values, Type targetType, object parameter, CultureInfo culture)
    {
        ListView listview = values[0] as ListView;
        double width = listview.ActualWidth;
        if (width == 0)
            return (double)parameter;

        //...
        return 100.0;
    }

    public object[] ConvertBack(object value, Type[] targetTypes, object parameter, CultureInfo culture)
    {
        throw new NotSupportedException();
    }
}

那么只要更新 ActualWidth 属性,就应该调用转换器。