Skip to content

Instantly share code, notes, and snippets.

@psurikov
Created February 10, 2019 21:44
Show Gist options
  • Save psurikov/506095e80b60ef94304b4688fc81a170 to your computer and use it in GitHub Desktop.
Save psurikov/506095e80b60ef94304b4688fc81a170 to your computer and use it in GitHub Desktop.
/// <summary>
/// Subscribes collection child item events to some specific handler.
/// The logic of subscription and unsubscription can be complicated,
/// considering that you need to take into account collection changes,
/// new child items have to subscribe, while unused and removed items
/// need to unsubscribe.
/// </summary>
public class CollectionSubscription<TItem, THandler>
{
private Action<TItem> subscribe;
private Action<TItem> unsubscribe;
private Action raiseEvent;
public CollectionSubscription(Action<TItem> subscribe, Action<TItem> unsubscribe, Action raiseEvent)
{
this.subscribe = subscribe;
this.unsubscribe = unsubscribe;
this.raiseEvent = raiseEvent;
}
public void Subscribe(ObservableCollection<TItem> collection)
{
collection.CollectionChanged -= OnCollectionChanged;
collection.CollectionChanged += OnCollectionChanged;
foreach (var item in collection)
{
unsubscribe(item);
subscribe(item);
}
}
public void Unsubscribe(ObservableCollection<TItem> collection)
{
collection.CollectionChanged -= OnCollectionChanged;
foreach (var item in collection)
unsubscribe(item);
}
private void OnCollectionChanged(object sender, NotifyCollectionChangedEventArgs e)
{
if (e.Action == NotifyCollectionChangedAction.Reset)
{
var collection = sender as IEnumerable<TItem>;
foreach (var item in collection)
{
unsubscribe(item);
subscribe(item);
}
}
var oldItems = e.OldItems as IEnumerable<TItem>;
if (oldItems != null)
{
foreach (var oldItem in oldItems)
unsubscribe(oldItem);
}
var newItems = e.NewItems as IEnumerable<TItem>;
if (newItems != null)
{
foreach (var newItem in newItems)
{
unsubscribe(newItem);
subscribe(newItem);
}
}
raiseEvent();
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment