我希望能够在Silverlight中拥有动态渐变,例如:
<RadialGradientBrush GradientOrigin="0.20,0.5" Center="0.25,0.50"
RadiusX="0.75" RadiusY="0.5">
<GradientStop Color="{Binding Path=GradientStart}" Offset="0" />
<GradientStop Color="{Binding Path=GradientEnd}" Offset="1" />
</RadialGradientBrush>
我绑定了两个返回“Color”类型的属性,但是我总是收到这条消息:
AG_E_PARSER_BAD_PROPERTY_VALUE
如果我尝试绑定到GradientStop Collection,这也有同样的问题,这个问题的解决方案是什么:
如果有工作或者无论如何要复制这种行为,这是可以接受的,我有解决方案可以使用LinearGradients,因为我可以将某些“Fill”属性绑定到此 - 但是在这种情况下无效,另外,我可能会使用其他渐变类型,其他人可能会在将来使用此解决方案/替代方案。
答案 0 :(得分:12)
问题是 GradientStop 不是从 FrameworkElement 派生的,因此无法绑定数据。不幸的是,这意味着你必须从代码中设置它。
答案 1 :(得分:5)
要真正做到这一点,你有两个选择。
将显示项Brush属性绑定到数据中的Brush属性
让数据源带有一个属性,该属性会为每个项目公开要使用的画笔,并绑定显示项目的属性,该属性包含画笔,例如Fill
属性。如果您对Start和Stop值对的一组不同值很小,则此方法有效。您将为每对创建每个画笔的实例,然后数据项将显示正确的画笔。
使用值转换器
绑定显示项目Brush属性如果“开始”和“停止”值为更多变量,则每个显示的项目都需要刷新类型的新实例。在这种情况下,您将使用值转换器绑定显示项刷属性,例如: -
<Rectangle Fill="{Binding Converter={StaticResource MyBrushBuilder} }" ... >
有关构建转换器的完整说明,请参阅此answer。
在这种情况下,虽然您的转换方法实现如下所示: -
public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
{
YourItemsType item = (YourItemsType)value;
var start = new GradientStop();
start.Offset = 0;
start.Color = item.GradientStart;
var stop = new GradientStop();
stop.Offset = 1;
stop.Color = item.GradientStop;
var result = new RadialGradientBrush();
result.GradientOrigin = new Point(0.20, 0.5);
result.Center = new Point(0.25, 0.5);
result.RadiusX = 0.75;
result.RadiusY = 0.5;
result.GradientStops = new GradientStopCollection();
result.GradientStops.Add(start);
result.GradientStops.Add(stop);
return result;
}
<强>买者强>
每当发生数据绑定时,会为每个项目创建一组刷子。这可能是昂贵且不合需要的。因此,如果认为这种绑定转换器方法是必要的,那么我建议你使用静态的画笔字典。这本词典的关键是两种颜色的哈希。您只需在必要时创建新画笔,并尽可能重复使用以前创建的画笔。
答案 2 :(得分:0)
您是否确认了用作定义渐变画笔的DataContext
的类型?由于您未在绑定中指定Source
,因此默认情况下会使用DataContext
。
答案 3 :(得分:0)
相当古老的帖子,但它可能(现在),所以这是我的解决方案。我的XAML代码:
<Ellipse.Resources>
<local:ColorConverter x:Key="ColorConverter"/>
</Ellipse.Resources>
<Ellipse.Fill>
<RadialGradientBrush>
<GradientStop Color="{Binding MenuColor2, Source={x:Static p:Settings.Default}, Converter={StaticResource ColorConverter}}" Offset="1" />
<GradientStop Color="{Binding MenuColor1, Source={x:Static p:Settings.Default}, Converter={StaticResource ColorConverter}}" Offset="0.85" />
</RadialGradientBrush>
</Ellipse.Fill>
这是我的C#-Code。
[ValueConversion(typeof(System.Drawing.Color), typeof(System.Windows.Media.Color))]
public class ColorConverter : IValueConverter
{
public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
{
if (value is System.Drawing.Color)
{
var clr = (System.Drawing.Color)value;
return System.Windows.Media.Color.FromArgb(clr.A, clr.R, clr.G, clr.B);
}
return value;
}
public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
{
if (value is Color)
{
var clr = (Color)value;
return System.Drawing.Color.FromArgb(clr.A, clr.R, clr.G, clr.B);
}
return value;
}
}