Files
TheXamlGuy/UI/WPF/PropertyChangedRevoker.cs
T
2022-11-01 15:26:08 +00:00

86 lines
2.7 KiB
C#

using System;
using System.Windows;
using System.Windows.Data;
namespace TheXamlGuy.UI.WPF
{
public class PropertyChangedRevoker : DependencyObject, IDisposable
{
public static readonly DependencyProperty ValueProperty =
DependencyProperty.Register(nameof(Value), typeof(object),
typeof(PropertyChangedRevoker), new PropertyMetadata(null, OnValuePropertyChanged));
private readonly WeakReference weakPropertySource;
public PropertyChangedRevoker(DependencyObject propertySource, string path,
DependencyPropertyChangedEventHandler valueChangedHandler) : this(propertySource, new PropertyPath(path),
valueChangedHandler)
{
}
public PropertyChangedRevoker(DependencyObject propertySource, DependencyProperty property,
DependencyPropertyChangedEventHandler valueChangedHandler) : this(propertySource,
new PropertyPath(property), valueChangedHandler)
{
}
public PropertyChangedRevoker(DependencyObject propertySource, PropertyPath property,
DependencyPropertyChangedEventHandler valueChangedHandler)
{
weakPropertySource = new WeakReference(propertySource);
Binding binding = new Binding
{
Path = property,
Mode = BindingMode.OneWay,
Source = propertySource
};
BindingOperations.SetBinding(this, ValueProperty, binding);
ValueChanged = valueChangedHandler;
Property = property;
}
public DependencyObject PropertySource
{
get
{
try
{
return weakPropertySource.IsAlive ? weakPropertySource.Target as DependencyObject : null;
}
catch
{
return null;
}
}
}
public object Value
{
get => GetValue(ValueProperty);
set => SetValue(ValueProperty, value);
}
public PropertyPath Property { get; }
public void Dispose()
{
BindingOperations.ClearBinding(this, ValueProperty);
}
private event DependencyPropertyChangedEventHandler ValueChanged;
private static void OnValuePropertyChanged(DependencyObject dependencyObject,
DependencyPropertyChangedEventArgs args)
{
PropertyChangedRevoker sender = dependencyObject as PropertyChangedRevoker;
sender?.OnValuePropertyChanged(args);
}
private void OnValuePropertyChanged(DependencyPropertyChangedEventArgs args)
{
ValueChanged?.Invoke(this, args);
}
}
}