2016-02-06 4 views
0

Я написал пользовательский элемент управления, и у меня есть две свойства зависимостей коллекции SourceA и SourceB. В приведенном ниже коде вы увидите, что свойства PropertyChanged свойств зависимостей точно такие же, кажется, что много избыточного кода.wpf INotifyCollectionChanged redundancy

SourceB_PropertyChanged... 
SourceA_PropertyChanged... 

Я не чувствую, что делаю это правильно. Есть ли способ удалить избыточность при сохранении изменений в Уведомлении для коллекции?

Кодекс

using System.Collections; 
using System.Collections.ObjectModel; 
using System.Collections.Specialized; 
using System.Windows; 
using System.Windows.Controls; 
using System.Windows.Media; 

namespace NexusEditor 
{ 
    /// <summary> 
    /// The main class that implements the network/flow-chart control. 
    /// </summary> 
    public partial class NexusEditor : Control 
    { 
     #region Dependency Property/Event Definitions 

     private static readonly DependencyPropertyKey ItemsPropertyKey = 
      DependencyProperty.RegisterReadOnly("Items", typeof(ObservableCollection<object>), typeof(NexusEditor), 
       new FrameworkPropertyMetadata()); 
     public static readonly DependencyProperty ItemsProperty = ItemsPropertyKey.DependencyProperty; 

     public static readonly DependencyProperty SourceAProperty = 
      DependencyProperty.Register("SourceA", typeof(IEnumerable), typeof(NexusEditor), 
       new FrameworkPropertyMetadata(SourceA_PropertyChanged)); 

     public static readonly DependencyProperty SourceBProperty = 
      DependencyProperty.Register("SourceB", typeof(IEnumerable), typeof(NexusEditor), 
       new FrameworkPropertyMetadata(SourceB_PropertyChanged)); 

     #endregion 


     #region Constructors 

     public NexusEditor() 
     { 
      // Create a collection to contain nodes. 
      this.Items = new ObservableCollection<object>(); 
     } 

     static NexusEditor() 
     { 
      DefaultStyleKeyProperty.OverrideMetadata(typeof(NexusEditor), new FrameworkPropertyMetadata(typeof(NexusEditor))); 
     } 

     #endregion 

     #region properties 

     public IEnumerable SourceA 
     { 
      get { return (IEnumerable)GetValue(SourceAProperty); } 
      set { SetValue(SourceAProperty, value); } 
     } 

     public IEnumerable SourceB 
     { 
      get { return (IEnumerable)GetValue(SourceBProperty); } 
      set { SetValue(SourceBProperty, value); } 
     } 

     /// <summary> 
     /// Collection of items 
     /// </summary> 
     public ObservableCollection<object> Items 
     { 
      get { return (ObservableCollection<object>)GetValue(ItemsProperty); } 
      private set { SetValue(ItemsPropertyKey, value); } 
     } 

     #endregion 

     #region privates 

     private static void UpdateItems(NexusEditor editor) 
     { 
      editor.Items.Clear(); 

      var sourceB = editor.SourceB as IEnumerable; 
      if (sourceB != null) 
      { 
       foreach (object obj in sourceB) 
       { 
        editor.Items.Add(obj); 
       } 
      } 

      var sourceA = editor.SourceA as IEnumerable; 
      if (sourceA != null) 
      { 
       foreach (object obj in sourceA) 
       { 
        editor.Items.Add(obj); 
       } 
      } 
     } 

     /// <summary> 
     /// Event raised when a new collection has been assigned to the SourceB property. 
     /// </summary> 
     private static void SourceB_PropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e) 
     { 
      NexusEditor c = (NexusEditor)d; 

      if (e.OldValue != null) 
      { 
       var notifyCollectionChanged = e.OldValue as INotifyCollectionChanged; 
       if (notifyCollectionChanged != null) 
       { 
        notifyCollectionChanged.CollectionChanged -= new NotifyCollectionChangedEventHandler(c.SourceB_CollectionChanged); 
       } 
      } 

      if (e.NewValue != null) 
      { 
       var notifyCollectionChanged = e.NewValue as INotifyCollectionChanged; 
       if (notifyCollectionChanged != null) 
       { 
        notifyCollectionChanged.CollectionChanged += new NotifyCollectionChangedEventHandler(c.SourceB_CollectionChanged); 
       } 
      } 

      UpdateItems(c); 
     } 

     /// <summary> 
     /// Event raised when a node has been added to or removed from the collection assigned to 'NodesSource'. 
     /// </summary> 
     private void SourceB_CollectionChanged(object sender, NotifyCollectionChangedEventArgs e) 
     { 
      UpdateItems(this); 
     } 


     /// <summary> 
     /// Event raised when a new collection has been assigned to the SourceB property. 
     /// </summary> 
     private static void SourceA_PropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e) 
     { 
      NexusEditor c = (NexusEditor)d; 

      if (e.OldValue != null) 
      { 
       var notifyCollectionChanged = e.OldValue as INotifyCollectionChanged; 
       if (notifyCollectionChanged != null) 
       { 
        notifyCollectionChanged.CollectionChanged -= new NotifyCollectionChangedEventHandler(c.SourceA_CollectionChanged); 
       } 
      } 

      if (e.NewValue != null) 
      { 
       var notifyCollectionChanged = e.NewValue as INotifyCollectionChanged; 
       if (notifyCollectionChanged != null) 
       { 
        notifyCollectionChanged.CollectionChanged += new NotifyCollectionChangedEventHandler(c.SourceA_CollectionChanged); 
       } 
      } 

      UpdateItems(c); 
     } 

     /// <summary> 
     /// Event raised when a node has been added to or removed from the collection assigned to 'NodesSource'. 
     /// </summary> 
     private void SourceA_CollectionChanged(object sender, NotifyCollectionChangedEventArgs e) 
     { 
      UpdateItems(this); 
     } 

     #endregion 

     public override void OnApplyTemplate() 
     { 
      base.OnApplyTemplate(); 

     } 
    } 
} 

ответ

1

Почему бы вам не создать метод один PropertyChanged обработчик с именем Source_PropertyChanged, например, и использовать это для обоих свойств зависимостей?

Если они точно такие же, вы можете просто сделать это.

public static readonly DependencyProperty SourceAProperty = 
    DependencyProperty.Register("SourceA", typeof(IEnumerable), typeof(NexusEditor), 
    new FrameworkPropertyMetadata(Source_PropertyChanged)); 

public static readonly DependencyProperty SourceBProperty = 
    DependencyProperty.Register("SourceB", typeof(IEnumerable), typeof(NexusEditor), 
    new FrameworkPropertyMetadata(Source_PropertyChanged)); 

Обработчик:

private static void Source_PropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e) 
{ 
    NexusEditor c = (NexusEditor)d; 

    if (e.OldValue != null) 
    { 
     var notifyCollectionChanged = e.OldValue as INotifyCollectionChanged; 
     if (notifyCollectionChanged != null) 
     { 
      notifyCollectionChanged.CollectionChanged -= new NotifyCollectionChangedEventHandler(c.Source_CollectionChanged); 
     } 
    } 

    if (e.NewValue != null) 
    { 
     var notifyCollectionChanged = e.NewValue as INotifyCollectionChanged; 
     if (notifyCollectionChanged != null) 
     { 
      notifyCollectionChanged.CollectionChanged += new NotifyCollectionChangedEventHandler(c.Source_CollectionChanged); 
     } 
    } 

    UpdateItems(c); 
} 

Для коллекции изменился:

private void Source_CollectionChanged(object sender, NotifyCollectionChangedEventArgs e) 
{ 
    UpdateItems(this); 
} 
+0

Удивительная это именно то, что я искал. Спасибо. – JokerMartini

Смежные вопросы