Tag: system.reactive

Rx:忽略订阅者导致的更新

我在弄清楚如何做到这一点时遇到了问题。 我有两个实现INotifyPropertyChanged实例(源和目标),我正在跟踪两者的PropertyChanged事件。 我想要做的是在任何时候运行一个动作source.PropertyChanged ,直到target.PropertyChanged被引发。 我可以这样做,就像这样: INotifyPropertyChanged source; INotifyPropertyChanged target; var sourcePropertyChanged = Observable .FromEvent(source, “PropertyChanged”) .Where(x => x.EventArgs.PropertyName == sourcePropertyName); var targetPropertyChanged = Observable .FromEvent(target, “PropertyChanged”) .Where(x => x.EventArgs.PropertyName == targetPropertyName); sourcePropertyChanged .TakeUntil(targetPropertyChanged) .ObserveOnDispatcher() .Subscribe(_ => /*Raises target.PropertyChanged for targetPropertyName*/); 我遇到的问题是我想忽略由操作引起的PropertyChanged通知,并且只有在外部源引发PropertyChanged事件时才停止获取值。 是否有一种很好的方法可以实现这一目标?

为什么这个双击检测代码不可靠?

我试图通过一些简单的挑战来学习Rx,首先通过仅观察MouseUp事件来检测双击。 我提出了以下解决方案(此代码可通过创建WPF项目并添加Reactive Extensions NuGet包来编译): using System; using System.Reactive.Linq; using System.Windows.Input; namespace WpfApplication1 { public partial class MainWindow { public MainWindow() { InitializeComponent(); var clickEvents = Observable .FromEventPattern(this, “MouseLeftButtonUp”); var intraClickInterval = TimeSpan.FromMilliseconds(500); var interClickInterval = TimeSpan.FromMilliseconds(1000); var doubleClicks = clickEvents .TimeInterval() .SkipWhile(t => t.Interval t.Interval Console.WriteLine(“Now accepting double click!”)); doubleClicks.Subscribe(e => Console.WriteLine(e.Interval)); } } } […]

正确合并从多个实例触发的事件的可观察序列的方法

假设我有一个工厂方法,可以生成类型为T的实例,并且我想要一个Rx可观察序列,用于从我的所有实例中触发的事件源自工厂方法。 正如我在下面所做的那样使用Merge()来实现这个目的的正确和最佳方式? 我这样做的另一种方法是使用一个静态事件并从中制作可观察序列,但是我通常不喜欢使用静态事件,并且很好奇Rx专家认为在这种情况下最优化的是什么? public T MakeFoo() where T: Foo, new() { this.instanceOfObservable.Merge(new T()); return self; } public class ObservableSequence : IObservable, IDisposable { private IObservable stream; public ObservableSequence() { } // this method is called in the factory method for each new instance of T public void Merge(Foo instance) { if (this.stream == null) { […]

任务列表中空条目的奇怪外观

这是涉及的代码: private static async Task DoRunInOrderAsync(SemaphoreSlim sem, IObservable taskSeedSource, CreateTaskDelegate createTask, OnTaskErrorDelegate onFailed, OnTaskSuccessDelegate onSuccess) where TTaskSeed : class { var tasks = await taskSeedSource .Select(taskSeed => GetPendingOrRunningTask(taskSeed, createTask, onFailed, onSuccess, sem)) .ToList() .ToTask(); await Task.WhenAll(tasks); } private static async Task GetPendingOrRunningTask(T taskSeed, CreateTaskDelegate createTask, OnTaskErrorDelegate onFailed, OnTaskSuccessDelegate onSuccess, SemaphoreSlim sem) where T : class […]

使用Rx确定鼠标拖动结束的正确方法是什么?

我正在慢慢学习如何使用WPF的.NET Reactive Extensions 。 有一些初学者的例子说明编写拖放或绘图例程是多么简单,但它们都非常简单。 我试图更进一步,对我来说,“正确”的方式是什么并不明显。 这些示例都展示了如何从MouseDown , MouseMove和MouseUp定义事件流 var mouseDown = from evt in Observable.FromEvent(…, “MouseDown”) select evt.EventArgs.GetPosition(…); var mouseMoves = from evt in Observable.FromEvent(…, “MouseMove”) select evt.EventArgs.GetPosition(…); var mouseUp = Observable.FromEvent(…, “MouseUp”); 然后如何在MouseDrag轻松完成任务(这会显示从起始拖动点到当前鼠标位置创建的矩形的坐标) var mouseDrag = from start in mouseDown from currentPosition in mouseMoves.TakeUntil(mouseUp) select new Rect(Math.Min(start.X, currentPosition.X), Math.Min(start.Y, currentPosition.Y), Math.Abs(start.X – currentPosition.X), […]

无功扩展定时器/间隔复位

我有一个项目,我需要每10秒发送一次状态消息,除非在此期间有更新。 意思是,每次有更新时,计时器都会重置。 var res = Observable .Interval(TimeSpan.FromSeconds(10)) .Where(_ => condition); res.Subscribe(_ => Console.WriteLine(“Status sent.”)); 现在我知道“Where”只会在计时器结束时应用,所以它没有帮助。 但是,我想知道是否有办法重置间隔; 或者使用带有重复的Timer()。

在WPF UserControl上使用Rx over事件,为什么当窗口最大化时控件会收到mousedown和mousemove?

这个让我有点困惑。 我在UIElement上编写了一些扩展方法,为一些鼠标事件提供Observable。 以下是相关的: public static IObservable<EventPattern> ObserveMouseLeftButtonDown(this UIElement element) { return Observable.FromEventPattern(element, “MouseLeftButtonDown”); } public static IObservable<EventPattern> ObserveMouseMove(this UIElement element) { return Observable.FromEventPattern(element, “MouseMove”); } 到目前为止,这简直令人费解。 然后我创建一个复合事件来检测用户何时开始拖动UIElement(这全部由我的自定义控件使用,其确切性质并不特别相关)。 首先,这是一个小辅助函数,用于查看用户是否拖动了最小拖动距离: private static bool MinimumDragSeen(Point start, Point end) { return Math.Abs(end.X – start.X) >= SystemParameters.MinimumHorizontalDragDistance || Math.Abs(end.Y – start.Y) >= SystemParameters.MinimumVerticalDragDistance; } 然后复合观察本身: public static IObservable<EventPattern> ObserveMouseDrag(this UIElement […]

RX:如何处理序列中的n个缓冲项,然后在处理下n个项之前等待t秒?

我想弄清楚如何处理序列中的n个缓冲项,然后在处理下n个项之前等待t秒? 这是我正在尝试做的粗略forms,使用Thread.Sleep()。 我想避免Thread.Sleep()并正确地执行它。 static void Main(string[] args) { var t = Observable.Range(0, 100000); var query = t.Buffer(20); query.ObserveOn(NewThreadScheduler.Default) .Subscribe(x => DoStuff(x)); Console.WriteLine(“Press ENTER to exit”); Console.ReadLine(); } static void DoStuff(IList list) { Console.WriteLine(DateTime.Now); foreach (var value in list) { Console.WriteLine(value); } Thread.Sleep(TimeSpan.FromSeconds(10)); } 任何人都可以帮我找到更多的RX方式吗? 谢谢 闪

我应该使用List 还是仅使用Action 来跟踪IObservable的订户?

我正在某些类上实现IObservable接口。 我使用Reflector来弄清楚这是如何在Rx中完成的。 关于观察者如何跟踪其订阅者并通过他们的OnNext方法通知他们,我偶然发现了与此类似的代码: private List<Observer> observers; // subscribe a new observer: public IDisposable Subscribe(IObserver observer) { observers.Add(observer); … } // trigger all observers’ OnNext method: … foreach (IObserver observer in observers) { observer.OnNext(value); } 由于所有代表都是多播的,因此不能简化为: Action observers; // subscribe observer: public IDisposable Subscribe(IObserver observer) { observers += observer.OnNext; … } // trigger observers’ OnNext: … […]

Reactive Framework(RX)和异步处理事件

所以我只是在玩RX并学习它。 我开始玩事件,并想知道如何订阅事件,并异步处理批量结果。 请允许我用代码解释: 引发事件的简单类: public class EventRaisingClass { public event EventHandler EventOccured; //some other code that raises event… } public class SomeEventArgs : EventArgs { public SomeEventArgs(int data) { this.SomeArg = data; } public int SomeArg { get; private set; } } 然后我的主要: public static void Main(string[] args) { var eventRaiser = new EventRaisingClass(); IObservable<IEvent> […]