Skip to content

Instantly share code, notes, and snippets.

@ViIvanov
Created February 6, 2014 16:57
Show Gist options
  • Save ViIvanov/8848200 to your computer and use it in GitHub Desktop.
Save ViIvanov/8848200 to your computer and use it in GitHub Desktop.
using System;
using System.ComponentModel;
using System.Diagnostics;
using System.Globalization;
namespace Xxx.ComponentModel
{
public abstract class CustomPropertyDescriptor : PropertyDescriptor
{
protected CustomPropertyDescriptor(MemberDescriptor descr) : base(descr) { }
protected CustomPropertyDescriptor(MemberDescriptor descr, Attribute[] attrs) : base(descr, attrs) { }
protected CustomPropertyDescriptor(string name, Attribute[] attrs) : base(name, attrs) { }
private bool IsSettingValue { get; set; }
private IDisposable SettingValue() {
Debug.Assert(!IsSettingValue, "UseSetValue: IsSettingValue == True");
IsSettingValue = true;
return Disposable.Create(() => {
Debug.Assert(IsSettingValue, "UseSetValue: IsSettingValue == False");
IsSettingValue = false;
});
}
protected virtual void OnValueChangedCore(object component, EventArgs e) {
base.OnValueChanged(component, e);
}
protected void OnComponentPropertyChanged(object component, PropertyChangedEventArgs e) {
if(e == null) {
throw new ArgumentNullException("e");
}//if
if(!IsSettingValue) {
if(String.IsNullOrEmpty(e.PropertyName) || String.Equals(Name, e.PropertyName, StringComparison.InvariantCultureIgnoreCase)) {
OnValueChanged(component, e);
}//if
}//if
}
protected abstract void SetValueCore(object component, object value);
public override bool SupportsChangeEvents {
[DebuggerStepThrough]
get { return typeof(INotifyPropertyChanged).IsAssignableFrom(PropertyType); }
}
public sealed override void SetValue(object component, object value) {
if(component == null) {
throw new ArgumentNullException("component");
}//if
using(SettingValue()) {
SetValueCore(component, value);
}//using
OnValueChanged(component, EventArgs.Empty);
}
public override void AddValueChanged(object component, EventHandler handler) {
if(GetValueChangedHandler(component) == null) {
var notify = component as INotifyPropertyChanged;
if(notify != null) {
notify.PropertyChanged += OnComponentPropertyChanged;
}//if
}//if
base.AddValueChanged(component, handler);
}
public override void RemoveValueChanged(object component, EventHandler handler) {
base.RemoveValueChanged(component, handler);
if(GetValueChangedHandler(component) == null) {
var notify = component as INotifyPropertyChanged;
if(notify != null) {
notify.PropertyChanged -= OnComponentPropertyChanged;
}//if
}//if
}
protected sealed override void OnValueChanged(object component, EventArgs e) {
if(!IsSettingValue) {
OnValueChangedCore(component, e);
}//if
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment