Table of Contents

Umstellung auf PropertyChanged

Die Components arbeiten nutzen jetzt das Event PropertyChanged um Änderungen an Properties zu kommunizieren. Sie implementieren dazu das Standard-Interface INotifyPropertyChanged.

Die bisher verwendeten Events, welche für jedes einzelne Component-Property sparat generiert wurden, entfallen. Wenn eigener Code existiert, der mit diesen Events arbeitet, muss dieser angepasst werden.

Im folgenden werden einige Situationen beschrieben.

Die Beispiele verwenden eine Component cdArticle mit den Properties sArticleID und sArticleName.

Event-Handler umstellen

Bisher gab es die folgenden Events

public event EventArgs sArticleIDChanged;
public event EventArgs sArticleNameChanged;

Diese wurden auf die folgende Weise verwendet:

// anhängen des Event-Handlers
oArticle.sArticleIDChanged += OnArticleIDHasChanged;

// Event-Handler-Methode
protected void OnArticleIDHasChanged(object sender, EventArgs args)
{
    // Code für geänderte Artikel-ID
}

// Event mit Lambda-Expression
oArticle.sArticleNameChanged += (sender, args) =>
{
    // Code für geänderte Artikel-Bezeichnung
};

Jetzt gibt es nur noch ein Event, welches in der Basis-Klasse DevFrameworkBaseObject implementiert ist.

public event PropertyChangedEventArgs PropertyChanged;

Dieses wird auf folgende Weise verwendet:

// anhängen des Event-Handlers
oArticle.PropertyChanged += OnArticleIDHasChanged;

// Event-Handler-Methode
protected void OnArticleIDHasChanged(object sender, PropertyChangedEventArgs args)
{
    if (args.IsProperty(nameof(IcdArticle.sArticleID)))
    {
        // Code für geänderte Artikel-ID
    }
}

// Event mit Lambda-Expression
oArticle.sArticleNameChanged += (sender, args) =>
{
    if (args.IsProperty(nameof(oArticle.sArticleName)))
    {
        // Code für geänderte Artikel-Bezeichnung
    }
};

Aufrufe von Fire-Methoden

Alter Code:

this.FiresArticleIDChanged();
this.FiresArticleNameChanged();

Neuer Code:

this.FirePropertyChanged(nameof(this.sArticleID));
this.FirePropertyChanged(nameof(this.sArticleName));

Muss man viele dieser Aufrufe ersetzen, kann man dafür im Code-Editor die Funktion Find/Replace verwenden.

  • Suche mir Regular Expression: this.Fire(?<prop>(?!Property)\w+)Changed\s*\(\s*\)
  • Ersetzen durch: this.FirePropertyChanged(nameof(this.${prop}))

StateChanged, IsModifiedChanged

Die Component-Properties State und IsModified, werden jetzt ebenfalls über PropertyChanged behandelt.

Die virtuellen Methoden OnStateChanged und OnIsModifiedChanged sind entfallen. Stattdessen kann diese Logik in die neue Methode OnPropertyChanged verschoben werden.

Alter Code:

protected override void OnStateChanged()
{
    // Status hat sich geändert
}
protected override void OnIsModifiedChanged()
{
    // IsModified hat sich geändert
}

Neuer Code:

protected override void OnPropertyChanged(string propertyName)
{
    // Base-Aufruf ist wichtig !!!
    base.OnPropertyChanged(propertyName);

    if (propertyName == nameof(this.State))
    {
        // Status hat sich geändert
    }
    if (propertyName == nameof(this.IsModified))
    {
        // IsModified hat sich geändert
    }
}

Neuer Code für Event-Handler:

// anhängen des Event-Handlers
oArticle.PropertyChanged += OnArticleStateChanged;

// Event-Handler-Methode
protected void OnArticleStateChanged(object sender, PropertyChangedEventArgs args)
{
    // Die Prüfung auf PropertyName == null macht hier keinen Sinn
    if (args?.PropertyName == nameof(this.State))
    {
        // Status hat sich geändert
    }
}

Reflection

Caution

Wenn die alten Changed-Events per Reflection angesprochen wurden, dann muss das gezielt umgebaut werden. Diese Fälle werden nicht durch den Compiler gefunden.

Mit einer Volltext-Suche nach folgendem Regulären Ausdruck könnten potentielle Stellen leicht gefunden werden:

  • \bEventInfo\b

Beispiel für einen problematischen Code:

System.Reflection.EventInfo oChangedEventInfo = this.oTarget.GetType().GetEvent(sPropertyNameP + "Changed");
if (oChangedEventInfo != null)
{
    oChangedEventInfo.AddEventHandler(this.oTarget, oXmlPropertyInfo.oChangedEventHandler);
}