使用ObservableAsPropertyHelper将Observables转化为Properties
使用WhenAny方法,可以监视对象属性的变化,并针对这些变化生成IObservable对象。但是有时候,我们想将这些生成的IObservable对象设置为一种输出属性。想象一下有这样一个场景,有一个取色器,用户能够通过3个Slide分别设置R,G,B值。每一个Slide可以使用ViewModel对象来表示,取值范围为0到255。为了显示结果,我们需要将RGB合成为一个XAML颜色对象。当RGB中的任何一个发生变化时,我们需要更新颜色属性。
实战效果:
实战代码
前端xaml很一般:
<Grid x:Name="LayoutRoot" Background="White"> <Grid.RowDefinitions> <RowDefinition/> <RowDefinition/> <RowDefinition/> <RowDefinition/> </Grid.RowDefinitions> <Grid.ColumnDefinitions> <ColumnDefinition /> <ColumnDefinition Width="auto"/> </Grid.ColumnDefinitions> <TextBlock Text="R(red):" HorizontalAlignment="Right"/> <Slider x:Name="RedSlider" Orientation="Horizontal" SmallChange="1" Maximum="255" Width="100" Grid.Column="1" Value="{Binding Redvalue,Mode=TwoWay}" /> <TextBlock Text="G(green):" Grid.Row="1" Grid.Column="0" HorizontalAlignment="Right"/> <Slider x:Name="GreenSlider" Grid.Row="1" Grid.Column="1" Orientation="Horizontal" SmallChange="1" Maximum="255" Width="100" Value="{Binding Greenvalue,Mode=TwoWay}"/> <TextBlock Text="B(blue):" HorizontalAlignment="Right" Grid.Row="2" Grid.Column="0" /> <Slider x:Name="BlackSlider" Grid.Row="2" Grid.Column="1" Orientation="Horizontal" SmallChange="1" Maximum="255" Width="100" Value="{Binding Bluevalue,Mode=TwoWay}"/> <Rectangle Fill="{Binding FinalColor,Mode=TwoWay}" Width="100" Height="109" Grid.Row="3" Grid.ColumnSpan="2"/> </Grid>
ViewModel代码:
public class MainPageViewModel : ReactiveObject { public MainPageViewModel() { IObservable<SolidColorBrush> color = this.WhenAny(x => x.Sumvalue, x => x.Redvalue, x => x.Greenvalue, x => x.Bluevalue, (a, r, g, b) =>new SolidColorBrush(Color.FromArgb(255, r.Value, g.Value, b.Value))); _finalColor = color.ToProperty(this, x => x.FinalColor); } #region Proerty public ObservableAsPropertyHelper<SolidColorBrush> _finalColor; public SolidColorBrush FinalColor { get { return _finalColor.Value; } } [IgnoreDataMember] public byte _sumvalue; public byte Sumvalue { get { return _sumvalue; } set { this.RaiseAndSetIfChanged(x => x.Sumvalue, value); } } [IgnoreDataMember] public byte _redvalue; public byte Redvalue { get { return _redvalue; } set { this.RaiseAndSetIfChanged(x => x.Redvalue, value); } } [IgnoreDataMember] public byte _greenvalue; public byte Greenvalue { get { return _greenvalue; } set { this.RaiseAndSetIfChanged(x => x.Greenvalue, value); } } [IgnoreDataMember] public byte _bluevalue; public byte Bluevalue { get { return _bluevalue; } set { this.RaiseAndSetIfChanged(x => x.Bluevalue, value); } } #endregion }
在学习RX中,WPF和Silverlight的环境是有区别的:
- WPF引用RX的dll可以直接在nuget中下载,而silverlight必须去官网下前一版本的。嫌费事可直接下载我的xap包引用。
- WPF中的类库远远大于silverlight的,例如上面的例子Color类,读者可自行msdn比较。
设置变量格式:
private void Application_Startup(object sender, StartupEventArgs e) { Func<string, string> UnderscoreFirstToLowerBehaviour = x => { char[] arr = x.ToCharArray(); arr[0] = char.ToLower(arr[0]); return '_' + new String(arr); }; RxApp.GetFieldNameForPropertyNameFunc = UnderscoreFirstToLowerBehaviour; this.RootVisual = new MainPage(); }
出处:http://www.cnblogs.com/luqixinhe/
作者:许欣欣
本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。