GitHub - Fody/PropertyChanged: Injects INotifyPropertyChanged code into properties at compile time (original) (raw)

NuGet Status

Injects code which raises the PropertyChanged event, into property setters of classes which implement INotifyPropertyChanged.

See Milestones for release notes.

This is an add-in for Fody

It is expected that all developers using Fody become a Patron on OpenCollective. See Licensing/Patron FAQ for more information.

Usage

See also Fody usage.

NuGet installation

Install the PropertyChanged.Fody NuGet package and update the Fody NuGet package:

PM> Install-Package Fody PM> Install-Package PropertyChanged.Fody

The Install-Package Fody is required since NuGet always defaults to the oldest, and most buggy, version of any dependency.

Add to FodyWeavers.xml

Add <PropertyChanged/> to FodyWeavers.xml

Overview

NOTE: All classes that implement INotifyPropertyChanged will have notification code injected into property setters.

Before code:

public class Person : INotifyPropertyChanged { public event PropertyChangedEventHandler PropertyChanged;

public string GivenNames { get; set; }
public string FamilyName { get; set; }
public string FullName => $"{GivenNames} {FamilyName}";

}

What gets compiled:

public class Person : INotifyPropertyChanged { public event PropertyChangedEventHandler PropertyChanged;

string givenNames;
public string GivenNames
{
    get => givenNames;
    set
    {
        if (value != givenNames)
        {
            givenNames = value;
            OnPropertyChanged(InternalEventArgsCache.GivenNames);
            OnPropertyChanged(InternalEventArgsCache.FullName);
        }
    }
}

string familyName;
public string FamilyName
{
    get => familyName;
    set 
    {
        if (value != familyName)
        {
            familyName = value;
            OnPropertyChanged(InternalEventArgsCache.FamilyName);
            OnPropertyChanged(InternalEventArgsCache.FullName);
        }
    }
}

public string FullName => $"{GivenNames} {FamilyName}";

protected void OnPropertyChanged(PropertyChangedEventArgs eventArgs)
{
    PropertyChanged?.Invoke(this, eventArgs);
}

}

internal static class InternalEventArgsCache { internal static PropertyChangedEventArgs FamilyName = new PropertyChangedEventArgs("FamilyName"); internal static PropertyChangedEventArgs FullName = new PropertyChangedEventArgs("FullName"); internal static PropertyChangedEventArgs GivenNames = new PropertyChangedEventArgs("GivenNames"); }

(the actual injected type and method names are different)

Code Generator

Starting with version 4 PropertyChanged.Fody ships with a C# code generator that can even more simplify your code by generating the boilerplate of the basic INotifyPropertyChanged implementation for you directly as source code.

Simply mark a class implementing INotifyPropertyChanged or having the [AddINotifyPropertyChangedInterface] attribute as partial and the generator will add the necessary event and event-invokers:

e.g. a class like this:

public partial class Class1 : INotifyPropertyChanged { public int Property1 { get; set; } public int Property2 { get; set; } }

will be complemented by the generator with this:

public partial class Class1 { public event PropertyChangedEventHandler? PropertyChanged; protected void OnPropertyChanged([CallerMemberName] string? propertyName = null) { OnPropertyChanged(new PropertyChangedEventArgs(propertyName)); } protected virtual void OnPropertyChanged(PropertyChangedEventArgs eventArgs) { PropertyChanged?.Invoke(this, eventArgs); } }

Code Generator Configuration

You can configure the code generator via properties in your project file:

false OnPropertyChanged

Workaround for WPF projects targeting multiple frameworks:

WPF projects targeting multiple frameworks may fail during the compilation of the *_wpftmp.csproj with

... error CS0111: Type 'SomeType' already defines a member called 'OnPropertyChanged' with the same parameter types

This can be fixed by adding this build target to your project:


Notes

public void OnPropertyChanged(string propertyName, object before, object after)  

For more information, see the wiki pages.

Icon

Icon courtesy of The Noun Project