System.Windows.Data 错误:5; FontSizeConverter 导致问题

Posted

技术标签:

【中文标题】System.Windows.Data 错误:5; FontSizeConverter 导致问题【英文标题】:System.Windows.Data Error: 5 ; FontSizeConverter is causing Problems 【发布时间】:2022-01-23 23:23:26 【问题描述】:

我正在努力解决这个错误 N°5。这是完整的错误信息:

System.Windows.Data 错误:5:BindingExpression 产生的值是 对目标属性无效。;值='0' 绑定表达式:路径=实际高度;数据项='网格' (名称='gridEingabemaske');目标元素是“文本框” (名称='txtabmessungStecknuss');目标属性是“FontSize”(类型 '双')

这是我目前所知道的: 我有一个 WPF-Control,它承载了很多文本框(具体来说是 118 个)。我还使用 FontSizeConverter 来操作文本框中的 FontSize。这个 FontSizeConverter 似乎会导致问题,因为它需要一个双值但得到一个 0(整数)。

我该如何解决这个问题?

我的 xaml 代码(最后只给你 118 个文本框中的 1 个):

<UserControl x:Class="SchrauberDB.Controls.Eingabemaske"
         xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
         xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
         xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
         xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
         xmlns:local="clr-namespace:SchrauberDB.View"
         xmlns:dm="clr-namespace:SchrauberDB.DataModel"
         mc:Ignorable="d" 
         d:DesignHeight="250" d:DesignWidth="1100"
         FontFamily="Arial">

<UserControl.Resources>

    <dm:FontSizeConverter x:Key="fontSizeCon" />

    <Style TargetType="x:Type Grid">
        <Style.Resources>
            <Style TargetType="x:Type Border">
                <Setter Property="CornerRadius" Value="50"/>

            </Style>
        </Style.Resources>
    </Style>
    <Style TargetType="x:Type StackPanel">
        <Setter Property="VerticalAlignment" Value="Center" />
        <Setter Property="HorizontalAlignment" Value="Left"/>
        <Setter Property="Margin" Value="20,0,0 ,0" />
        <Style.Resources>
            <Style TargetType="x:Type TextBlock">
                <Setter Property="FontSize" Value="18" />

                <Setter Property="FontFamily" Value="Arial" />
                <Setter Property="FontWeight" Value="Medium" />
            </Style>
        </Style.Resources>
    </Style>
    <Style TargetType="x:Type TextBox">
        <Style.Resources>
            <Style TargetType="x:Type Border">
                <Setter Property="CornerRadius" Value="5"/>
                <Setter Property="BorderBrush" Value="#6A767D" />
            </Style>
        </Style.Resources>
        <Setter Property="Width" Value="160" />
        <Setter Property="Height" Value="30" />
        <Setter Property="BorderBrush" Value="#6A767D" />
        <Setter Property="Background" Value="#C2CACF" />

    </Style>
</UserControl.Resources>

<Grid x:Name="gridEingabemaske" Background="#FEFFFF" >

    <Grid.ColumnDefinitions>
        <ColumnDefinition Width="400"/>
        <ColumnDefinition />
        <ColumnDefinition Width="200"/>
    </Grid.ColumnDefinitions>
    <Grid.RowDefinitions>
        <RowDefinition/>
        <RowDefinition/>
    </Grid.RowDefinitions>

    <Button Grid.Column="3" Grid.Row="0" 
            Height="45" Width="160">
        <TextBlock FontSize="14" FontWeight="Medium">
            Speichern
        </TextBlock>
    </Button>
    <Button Grid.Column="3" Grid.Row="1" 
            Height="45" Width="160" Click="Button_CreateBemi_Click" 
            >
        <TextBlock  FontSize="14" FontWeight="Medium">
            Neues Bemi Anlegen
        </TextBlock>
    </Button>

    <ListView x:Name="lvEingabe" Margin="25" Grid.RowSpan="2">
        <ListView.ItemContainerStyle>
            <Style TargetType="ListViewItem">
                <EventSetter Event="PreviewMouseLeftButtonDown" Handler="ListViewItem_PreviewMouseLeftButtonDown" />
            </Style>
        </ListView.ItemContainerStyle>
    </ListView>

    <StackPanel x:Name="abmessungStecknuss" Visibility="Hidden">
        <TextBlock>Abmessung Stecknuss</TextBlock>
        <TextBox x:Name="txtabmessungStecknuss" Text="Binding Path=abmessungStecknuss" KeyDown="OnKeyDownHandler" FontSize="Binding Path=ActualHeight, RelativeSource=RelativeSource Mode=FindAncestor, AncestorType=Grid, Converter=StaticResource fontSizeCon"></TextBox>
    </StackPanel>
    
    ...

这是我的 FontSizeConverter 类:

namespace SchrauberDB.DataModel

    public class FontSizeConverter : IValueConverter
    
        public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        
            double actualHeight = System.Convert.ToDouble(value);
            int fontSize = (int)(actualHeight * .05);
            return fontSize;
        

        public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        
            throw new NotImplementedException();
        
    

【问题讨论】:

为什么要显式强制转换为 int? return actualHeight * .05; 我已经尝试过您的方法,但没有奏效。我仍然遇到同样的错误... 【参考方案1】:

doubleint 的演员表是多余的。你应该删除它。此外,不要抛出NotImplementedException 异常。如果不支持ConvertBack 方法,则抛出NotSupportedException

这里的问题是,根据错误消息,ActualHeight 的值是0。虽然0 是有效高度,但对于FontSize 来说它是非法值。

消息:

“BindingExpression 生成的值对目标无效” 然后它声明该值为"Value='0'" 目标是“目标元素是'TextBox'” 目标属性"目标属性是 'FontSize'"

消息清楚地传达了无效的,而不是无效的类型! 错误消息转换为:“0 的值对于 TextBox.FontSize 属性无效。”

了解了这些知识后,您现在可以查阅 Control.FontSize 属性的 API 参考。从这里你可以学到:

字体大小必须为正数。

从我们的数学课中,我们知道零不是正数。 发现问题。解决办法很明显:防止非法的转换器值。

这意味着,您应该为您的转换器实现添加一些稳健性:

public class FontSizeConverter : IValueConverter

  public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
  
    double actualHeight = System.Convert.ToDouble(value);
    double fontSize = actualHeight * .05;
    return Math.Max(0.1, fontSize);

    // Alternatively return a default value e.g., 12
    return fontsize == 0 ? 12 : fontsize
  

  public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
  
    throw new NotSupportedException();
  

【讨论】:

它有效...谢谢!

以上是关于System.Windows.Data 错误:5; FontSizeConverter 导致问题的主要内容,如果未能解决你的问题,请参考以下文章

在 WPF 中使用 DataTable 和 DataGrid 时发生 System.Windows.Data 错误

WPF 管理 FrameworkElement 未找到错误

Source=null 的 ImageSourceConverter 错误

找不到WPF绑定属性

BindingExpression 路径错误:在“对象”上找不到属性

WPF datagrid.rowstyle 绑定