Рефакторинг PropertyChangedEventHandler - PullRequest
4 голосов
/ 02 февраля 2010

В моем коде пользовательского интерфейса у меня много классов с одинаковым базовым скелетом:

  • происходит от INotifyPropertyChanged
  • содержит следующий код:

    void NotifyPropertyChanged(String info)
    {
        if (PropertyChanged != null)
        {
            PropertyChanged(this, new PropertyChangedEventArgs(info));
        }
    }
    
    public event PropertyChangedEventHandler PropertyChanged;
    

Кажется, что это идеальный шанс включить в класс и извлечь из него вместо INotifyPropertyChanged, но, к сожалению, C # не поддерживает множественное наследование, поэтому на самом деле он не будет работать. Любые идеи о том, как рефакторинг такого рода кода?

Ответы [ 5 ]

1 голос
/ 02 февраля 2010

Обычной практикой является использование базового класса, реализующего INotifyPropertyChanged, например:

public abstract class ViewModelBase : INotifyPropertyChanged
{
    public event PropertyChangedEventHandler PropertyChanged;

    protected void OnPropertyChanged(string propertyName)
    {
        PropertyChangedEventHandler handler = PropertyChanged;

        if (handler != null)
        {
            handler(this, new PropertyChangedEventArgs(propertyName));
        }
    }
}

Тогда ваши классы будут производными от этого, и вы можете вызывать OnPropertyChanged, когда хотите уведомить об изменениях значения свойства:

public class PersonViewModel : ViewModelBase
{

    public PersonViewModel(Person person)
    {
        this.person = person;
    }

    public string Name
    {
        get
        {
            return this.person.Name;
        }
        set
        {
            this.person.Name = value;
            OnPropertyChanged("Name");
        }
    }
}
1 голос
/ 02 февраля 2010

Разве вы не можете просто поместить этот код в суперкласс вашего суперкласса?

  • Объект
    • Ваш конкретный класс NotifyPropertyChanged
      • От чего унаследована ваша модель представления (и она остановила вас при использовании множественного наследования
        • Ваша конкретная модель представления
        • Еще одна конкретная модель вида

Большинство MVVM Framework предоставляет такой класс для вас.

Из-за правил доступа к событиям, вы, к сожалению, не можете включить это в метод расширения без размышления.

1 голос
/ 02 февраля 2010

Может быть, вы можете использовать что-то вроде этого:

class A1 : INotifyPropertyChanged
{
    private string _myProperty;
    private static Expression<Func<A1, string>> myProperty = _ => _.MyProperty;

    public string MyProperty
    {
        get { return _myProperty; }
        set
        {
            _myProperty = value;
            InvokePropertyChanged(myProperty);
        }
    }

    public event PropertyChangedEventHandler PropertyChanged;

    private void InvokePropertyChanged<T>(Expression<Func<A1, T>> property)
    {
        PropertyChangedEventHandler Handler = PropertyChanged;
        if (Handler != null)
        {
            MemberExpression expression = (MemberExpression)property.Body;
            Handler(this, new PropertyChangedEventArgs(expression.Member.Name));
        }
    }
}

Это значительно уменьшает будущие изменения кода;)

Или вы можете использовать Плагин Postsharp, автоматически реализующий INotifyPropertyChanged .

0 голосов
/ 17 августа 2011

Это, вероятно, небольшая справка, но вы можете использовать ключевое слово params, чтобы вы могли изменять более одного свойства одновременно.

    public event PropertyChangedEventHandler PropertyChanged;

    public void NotifyPropertiesChanged(params string[] Properties)
    {
        if (PropertyChanged != null)
            foreach (string property in Properties)
                PropertyChanged(this, new PropertyChangedEventArgs(property));
    }

Это уменьшает количество строк, которые вы используете при уведомлении об изменениях свойств в будущем. Итак, вы используете:

NotifyPropertiesChanged ("foo", "bar");

Вместо:

NotifyPropertyChanged ( "Foo"); NotifyPropertyChanged ( "бар");

В противном случае я согласен с предложением Андерса поднять его вверх по дереву наследования, вероятно, было бы лучше

0 голосов
/ 02 февраля 2010

Это 4 строки кода, которые никогда не изменятся. Создать фрагмент!

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...