Xaml - 在 FallBackValue 中绑定
Xaml - Binding in FallBackValue
我如何在网格中的列上进行两个绑定,如果第一个绑定为空或 null,将使用第二个绑定。我曾尝试使用 FallbackValue 属性 来做到这一点,但您不能仅在其中绑定静态值。
这里有一些代码,这不仅仅是文字!
<telerik:RadGridView x:Name="radGridView">
<telerik:RadGridView.Columns>
<telerik:GridViewDataColumn DataMemberBinding="{Binding FirstName,
FallbackValue=Binding FirstName2}" //You cant do that!
Header="First Name" />
</telerik:RadGridView.Columns>
</telerik:RadGridView>
xaml一定有办法做到!请帮忙!
你可以为此使用 DataTriggers,像这样
<telerik:RadGridView x:Name="radGridView">
<telerik:RadGridView.Columns>
<telerik:GridViewDataColumn Header="First Name">
<telerik:GridViewDataColumn.Style>
<Style TargetType="{x:Type telerik:GridViewDataColumn}">
<Setter Property="DataMemberBinding" Value="{Binding FirstName}"/>
<Style.Triggers>
<DataTrigger Binding="{Binding FirstName}" Value="{x:Null}">
<Setter Property="DataMemberBinding" Value="{Binding FirstName2}"/>
</DataTrigger>
</Style.Triggers>
</Style>
</telerik:GridViewDataColumn.Style>
</telerik:GridViewDataColumn>
</telerik:RadGridView.Columns>
</telerik:RadGridView>
我至少能想到两个办法:
第一个解决方案(在 DataContext 中解决): 将 属性 添加到您的 DataContext
类型,例如 ResolvedFirstName 并且该值取自 FirstName 或 FirstName2,并且当两者中的任何一个发生更改时 ResolvedFirstName 重新评估。
public string ResolvedFirstName {
get { return string.IsNullOrEmpty(FirstName) ? FirstName2 : FirstName; }
}
public string FirstName {
get {...}
set {...
RaisePropertyChanged("FirstName");
RaisePropertyChanged("ResolvedFirstName");}
}
public string FirstName2 {
get {...}
set {...
RaisePropertyChanged("FirstName2");
RaisePropertyChanged("ResolvedFirstName");}
}
第二个解决方案(在视图中解决): 添加一个 StringMultiplexer
作为 StaticResource
绑定到两个属性,它提供了一个 Output 属性 你的专栏可以绑定。
<RadGridView>
<RadGridView.Resources>
<StringMultiplexer x:Key="FirstNameMux"
HighPrioString="{Binding FirstName}"
LowPrioString="{Binding FirstName2}"/>
</RadGridView.Resources>
<RadGridView.Columns>
<GridViewDataColumn
DataMemberBinding="{Binding Output, Source={StaticResource FirstNameMux}}"/>
和代码:
public class StringMultiplexer : DependencyObject
{
public string LowPrioString
{
get { return (string) GetValue( LowPrioStringProperty ); }
set { SetValue( LowPrioStringProperty, value ); }
}
public static readonly DependencyProperty LowPrioStringProperty =
DependencyProperty.Register( "LowPrioString", typeof( string ), typeof( StringMultiplexer ), new PropertyMetadata( DetermineOutput ) );
public string HighPrioString
{
get { return (string) GetValue( HighPrioStringProperty ); }
set { SetValue( HighPrioStringProperty, value ); }
}
public static readonly DependencyProperty HighPrioStringProperty =
DependencyProperty.Register( "HighPrioString", typeof( string ), typeof( StringMultiplexer ), new PropertyMetadata( DetermineOutput ) );
public string Output
{
get { return (string) GetValue( OutputProperty ); }
set { SetValue( OutputProperty, value ); }
}
public static readonly DependencyProperty OutputProperty =
DependencyProperty.Register( "Output", typeof( string ), typeof( StringMultiplexer ), null );
private static void DetermineOutput( DependencyObject d, DependencyPropertyChangedEventArgs e )
{
((StringMultiplexer) d).DetermineOutput();
}
private void DetermineOutput()
{
Output = (string.IsNullOrEmpty( HighPrioString )) ? LowPrioString : HighPrioString;
}
}
当我输入第二个解决方案时,我开始怀疑这个解决方案是否适用于您的具体情况。我自己使用了 StringMultiplexer
并且它按预期工作。我在你的案例中看到的问题是:GridViewDataColumn 不是 FrameworkElement(据我所知),而只是一个 Column-definition-object,它为实际单元格控件或行控件实例化时提供蓝图,而 DataMemberBinding 将最可能针对为其创建行的项目对象进行解析。也许您需要从 GridViewDataColumn 派生并在那里实现多路复用器。
我如何在网格中的列上进行两个绑定,如果第一个绑定为空或 null,将使用第二个绑定。我曾尝试使用 FallbackValue 属性 来做到这一点,但您不能仅在其中绑定静态值。 这里有一些代码,这不仅仅是文字!
<telerik:RadGridView x:Name="radGridView">
<telerik:RadGridView.Columns>
<telerik:GridViewDataColumn DataMemberBinding="{Binding FirstName,
FallbackValue=Binding FirstName2}" //You cant do that!
Header="First Name" />
</telerik:RadGridView.Columns>
</telerik:RadGridView>
xaml一定有办法做到!请帮忙!
你可以为此使用 DataTriggers,像这样
<telerik:RadGridView x:Name="radGridView">
<telerik:RadGridView.Columns>
<telerik:GridViewDataColumn Header="First Name">
<telerik:GridViewDataColumn.Style>
<Style TargetType="{x:Type telerik:GridViewDataColumn}">
<Setter Property="DataMemberBinding" Value="{Binding FirstName}"/>
<Style.Triggers>
<DataTrigger Binding="{Binding FirstName}" Value="{x:Null}">
<Setter Property="DataMemberBinding" Value="{Binding FirstName2}"/>
</DataTrigger>
</Style.Triggers>
</Style>
</telerik:GridViewDataColumn.Style>
</telerik:GridViewDataColumn>
</telerik:RadGridView.Columns>
</telerik:RadGridView>
我至少能想到两个办法:
第一个解决方案(在 DataContext 中解决): 将 属性 添加到您的 DataContext
类型,例如 ResolvedFirstName 并且该值取自 FirstName 或 FirstName2,并且当两者中的任何一个发生更改时 ResolvedFirstName 重新评估。
public string ResolvedFirstName {
get { return string.IsNullOrEmpty(FirstName) ? FirstName2 : FirstName; }
}
public string FirstName {
get {...}
set {...
RaisePropertyChanged("FirstName");
RaisePropertyChanged("ResolvedFirstName");}
}
public string FirstName2 {
get {...}
set {...
RaisePropertyChanged("FirstName2");
RaisePropertyChanged("ResolvedFirstName");}
}
第二个解决方案(在视图中解决): 添加一个 StringMultiplexer
作为 StaticResource
绑定到两个属性,它提供了一个 Output 属性 你的专栏可以绑定。
<RadGridView>
<RadGridView.Resources>
<StringMultiplexer x:Key="FirstNameMux"
HighPrioString="{Binding FirstName}"
LowPrioString="{Binding FirstName2}"/>
</RadGridView.Resources>
<RadGridView.Columns>
<GridViewDataColumn
DataMemberBinding="{Binding Output, Source={StaticResource FirstNameMux}}"/>
和代码:
public class StringMultiplexer : DependencyObject
{
public string LowPrioString
{
get { return (string) GetValue( LowPrioStringProperty ); }
set { SetValue( LowPrioStringProperty, value ); }
}
public static readonly DependencyProperty LowPrioStringProperty =
DependencyProperty.Register( "LowPrioString", typeof( string ), typeof( StringMultiplexer ), new PropertyMetadata( DetermineOutput ) );
public string HighPrioString
{
get { return (string) GetValue( HighPrioStringProperty ); }
set { SetValue( HighPrioStringProperty, value ); }
}
public static readonly DependencyProperty HighPrioStringProperty =
DependencyProperty.Register( "HighPrioString", typeof( string ), typeof( StringMultiplexer ), new PropertyMetadata( DetermineOutput ) );
public string Output
{
get { return (string) GetValue( OutputProperty ); }
set { SetValue( OutputProperty, value ); }
}
public static readonly DependencyProperty OutputProperty =
DependencyProperty.Register( "Output", typeof( string ), typeof( StringMultiplexer ), null );
private static void DetermineOutput( DependencyObject d, DependencyPropertyChangedEventArgs e )
{
((StringMultiplexer) d).DetermineOutput();
}
private void DetermineOutput()
{
Output = (string.IsNullOrEmpty( HighPrioString )) ? LowPrioString : HighPrioString;
}
}
当我输入第二个解决方案时,我开始怀疑这个解决方案是否适用于您的具体情况。我自己使用了 StringMultiplexer
并且它按预期工作。我在你的案例中看到的问题是:GridViewDataColumn 不是 FrameworkElement(据我所知),而只是一个 Column-definition-object,它为实际单元格控件或行控件实例化时提供蓝图,而 DataMemberBinding 将最可能针对为其创建行的项目对象进行解析。也许您需要从 GridViewDataColumn 派生并在那里实现多路复用器。