My goal is to extend the Collection object to support to flag when an item is added, updated or removed from the Collection. The MSDN article provides an example (Example 2) of extending for a specific type. I would like to keep it Generic so I don’t have to implemnent a new Class for every Collection I have.
Here is what I have so far:
public class ChangedEventArgs<T> : EventArgs
{
public readonly T ChangedItem;
public readonly T ReplacedWith;
public readonly ChangeType ChangeType;
public ChangedEventArgs(ChangeType change, T item, T replacement)
{
ChangeType = change;
ChangedItem = item;
ReplacedWith = replacement;
}
}
public enum ChangeType
{
Added,
Removed,
Replaced,
Cleared
};
class CollectionChangeTracked<T> : Collection<T>
{
public event EventHandler<ChangedEventArgs<T>> Changed;
protected override void InsertItem<TParam>(int index, TParam newItem)
{
base.InsertItem(index, newItem);
EventHandler<ChangedEventArgs<T>> temp = Changed;
if (temp != null)
{
temp(this, new ChangedEventArgs<T>(ChangeType.Added, newItem, null));
}
}
protected override void SetItem<TParam>(int index, TParam newItem)
{
string replaced = Items[index];
base.SetItem(index, newItem);
EventHandler<ChangedEventArgs<T>> temp = Changed;
if (temp != null)
{
temp(this, new ChangedEventArgs(ChangeType.Replaced, replaced, newItem));
}
}
protected override void RemoveItem<TParam>(int index)
{
TParam removedItem = Items[index];
base.RemoveItem(index);
EventHandler<ChangedEventArgs<T>> temp = Changed;
if (temp != null)
{
temp(this, new ChangedEventArgs<T>(ChangeType.Removed, removedItem, null));
}
}
protected override void ClearItems()
{
base.ClearItems();
EventHandler<ChangedEventArgs<T>> temp = Changed;
if (temp != null)
{
temp(this, new ChangedEventArgs(ChangeType.Cleared, null, null));
}
}
}
Question:
I’m receiving an error on the line: base.InsertItem(index, newItem)
It says I have invalid arguments but nothing more. Same issue in SetItem and RemoveItem.
Updated code that compiles:
public class ChangedEventArgs<T> : EventArgs
{
public readonly T ChangedItem;
public readonly T? ReplacedWith;
public readonly ChangeType ChangeType;
public ChangedEventArgs(ChangeType change, T item, T? replacement)
{
ChangeType = change;
ChangedItem = item;
ReplacedWith = replacement;
}
}
public enum ChangeType
{
Added,
Removed,
Replaced,
Cleared
};
class CollectionChangeTracked<T> : Collection<T>
{
public event EventHandler<ChangedEventArgs<T>> Changed;
protected override void InsertItem(int index, T newItem)
{
base.InsertItem(index, newItem);
EventHandler<ChangedEventArgs<T>> temp = Changed;
if (temp != null)
temp(this, new ChangedEventArgs<T>(ChangeType.Added, newItem, default(T)));
}
protected override void SetItem(int index, T newItem)
{
T replaced = Items[index];
base.SetItem(index, newItem);
EventHandler<ChangedEventArgs<T>> temp = Changed;
if (temp != null)
temp(this, new ChangedEventArgs<T>(ChangeType.Replaced, replaced, newItem));
}
protected override void RemoveItem(int index)
{
T removedItem = Items[index];
base.RemoveItem(index);
EventHandler<ChangedEventArgs<T>> temp = Changed;
if (temp != null)
temp(this, new ChangedEventArgs<T>(ChangeType.Removed, removedItem, null));
}
protected override void ClearItems()
{
base.ClearItems();
EventHandler<ChangedEventArgs<T>> temp = Changed;
if (temp != null)
temp(this, new ChangedEventArgs<T>(ChangeType.Cleared, null, null));
}
@daveL is totally right, what you want is a generic event args:
But what he has missed in his answer is how to use it; first make your event handler use the same type
Tas the main class:Then, your individual methods, rather than redefining the type as
TParamshould be using theTdefined at class level:Live example: http://rextester.com/XFCLN26271