Skip to content

Instantly share code, notes, and snippets.

@chuckdee68
Created June 13, 2014 20:19
Show Gist options
  • Save chuckdee68/423130be477b70dab464 to your computer and use it in GitHub Desktop.
Save chuckdee68/423130be477b70dab464 to your computer and use it in GitHub Desktop.
NotifyingObject - Making Magic Strings not a necessity for INotifyPropertyChanged
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Linq.Expressions;
using System.Text;
namespace Supporting
{
/// <summary>
/// One of the things that annoys me about notifypropertychanged is the
/// use of magic strings. This base class implements INotifyPropertyChanged
/// in a way that when you notify on a property, you use a lambda for
/// the actual property- therefore if it changes, it won't compile.
///
/// The same is used to check what property changed on the subscriber
/// side.
/// </summary>
/// <example>
/// Publisher side -
/// private object _ObservableProperty = null;
/// public object ObservableProperty
/// {
/// get
/// {
/// return this._ObservableProperty;
/// }
/// protected set
/// {
/// if (value != this._ObservableProperty)
/// {
/// this._ObservableProperty = value;
/// ---> this.NotifyPropertyChanged(() => this.ObservableProperty);
/// }
/// }
/// }
///
/// Subscriber side
/// void Publisher_PropertyChanged(object sender, System.ComponentModel.PropertyChangedEventArgs e)
/// {
/// if (e.PropertyName == NotifyingObject.GetPropertyName(() => this.Publisher.ObservableProperty))
/// {
/// //-- do some stuff
/// }
/// }
/// </example>
public abstract class NotifyingObject : INotifyPropertyChanged
{
public static string GetPropertyName<TProperty>(Expression<Func<TProperty>> property)
{
var lambda = (LambdaExpression)property;
MemberExpression memberExpression;
if (lambda.Body is UnaryExpression)
{
var unaryExpression = (UnaryExpression)lambda.Body;
memberExpression = (MemberExpression)unaryExpression.Operand;
}
else
memberExpression = (MemberExpression)lambda.Body;
return memberExpression.Member.Name;
}
#region INotifyPropertyChanged Implementation
public event PropertyChangedEventHandler PropertyChanged;
protected virtual void OnPropertyChanged(string propertyName)
{
PropertyChangedEventHandler handler = this.PropertyChanged;
if (handler != null)
{
var e = new PropertyChangedEventArgs(propertyName);
handler(this, e);
}
}
protected void NotifyPropertyChanged<TProperty>(Expression<Func<TProperty>> property)
{
this.OnPropertyChanged(NotifyingObject.GetPropertyName(property));
}
#endregion
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment