念のため、これからはこのパターンを使用します。私はおそらく拡張メソッドを介して動作するように変更しますが、原則は健全です。ドロップしたいサブスクリプションをリークしないようにするため
class Mesh2D{
public Mesh2D()
{
DisposeOnUnload(CreateBindings());
}
// Register all disposables for disposal on
// UIElement.Unload event. This should be
// moved to an extension method.
void DisposeOnUnload(IEnumerable<IDisposable> disposables)
{
var d = new CompositeDisposable(disposables);
var d2 = this.UnloadedObserver()
.Subscribe(e => d.Dispose());
var d3 = this.Dispatcher.ShutdownStartedObserver()
.Subscribe(e => d.Dispose());
d.Add(d2);
d.Add(d3);
}
// Where your bindings are simply yielded and
// they are removed on Unload magically
IEnumerable<IDisposable> CreateBindings()
{
// When the size changes we need to update all the transforms on
// the markers to reposition them.
yield return this.SizeChangedObserver()
.Throttle(TimeSpan.FromMilliseconds(20), RxApp.DeferredScheduler)
.Subscribe(eventArgs => this.ResetImageSource());
// If the points change or the viewport changes
yield return this.WhenAny(t => t.Mesh, t => t.Viewport, (x, t) => x.Value)
.Throttle(TimeSpan.FromMilliseconds(20), RxApp.DeferredScheduler)
.Subscribe(t => this.UpdateMeshChanged());
}
}
注: RX FromEventPattern を自動的に生成された拡張メソッドでラップしているため、覚えにくい FromEventPattern の形式ではなく、無料で SizeChangedObserver() と UnloadedObserver() を取得します。
ラッピングコードはそのまま生成されます
public static IObservable<EventPattern<RoutedEventArgs>> UnloadedObserver(this FrameworkElement This){
return Observable.FromEventPattern<RoutedEventHandler, RoutedEventArgs>(h => This.Unloaded += h, h => This.Unloaded -= h);
}
上記のパターンは、おそらく IDisposable ビュー モデルのバインドを解除するためにも使用できます。