dotnet / wpf

WPF is a .NET Core UI framework for building Windows desktop applications.
MIT License
7.05k stars 1.17k forks source link

Application.LoadComponent throws exception when loading XAML resource with AttachedProperty inconsistently #3813

Open UsuarioBeta opened 3 years ago

UsuarioBeta commented 3 years ago

This is a quick summary of how this issue was found and the attempts made to narrow it's source:

  1. The issue was first encountered in a F# WPF application while adding a Interaction.Behaviors (from microsoft/XamlBehaviorsWpf) to a custom Control.

  2. Upon inquiry to the aforementioned XamlBehaviorsWpf GitHub (here), it was determined that this issue was reproducible in C# and reproducible using a simple dummy attached property.

  3. While trying to determine whether this issue was reproducible in both .NET Core 3.0 and .NET Framework 4.8, I found that it may be actually something more subtle causing this exception to be thrown, as it would inconsistently occur between F# and C#, between .NET Core 3.0 and .NET Framework 4.8 and between Interaction.Triggers and a dummy AttachedProperty. These attempts are all included in the repro solution, and I tried to make it easy to understand both the attempt and the result. This is a summary:

  1. This is my personal guess, please be aware I have but little understanding of the inner workings of WPF. I think, as the exception message suggests, that the member created when an AttachedProperty is assigned using DependencyProperty.RegisterAttached in C# is sometimes invisible to Application.LoadComponent, causing the crash. My conclusion is supported by the following:
System.Windows.Markup.XamlParseException
  HResult=0x80131501
  Message='Cannot set unknown member '{clr-namespace:ReproAttachedPropertyCore30.CSharp.Fail}DummyAttached.Foo'.' Line number '11' and line position '6'.
  Source=PresentationFramework
  StackTrace:
   at System.Windows.Markup.XamlReader.RewrapException(Exception e, IXamlLineInfo lineInfo, Uri baseUri)
   at System.Windows.Markup.WpfXamlLoader.Load(XamlReader xamlReader, IXamlObjectWriterFactory writerFactory, Boolean skipJournaledProperties, Object rootObject, XamlObjectWriterSettings settings, Uri baseUri)
   at System.Windows.Markup.WpfXamlLoader.Load(XamlReader xamlReader, Boolean skipJournaledProperties, Uri baseUri)
   at System.Windows.Markup.XamlReader.Load(XamlReader xamlReader, ParserContext parserContext)
   at System.Windows.Markup.XamlReader.Load(XmlReader reader, ParserContext parserContext, XamlParseMode parseMode, Boolean useRestrictiveXamlReader, List`1 safeTypes)
   at System.Windows.Markup.XamlReader.Load(Stream stream, ParserContext parserContext, Boolean useRestrictiveXamlReader)
   at System.Windows.Markup.XamlReader.Load(Stream stream, ParserContext parserContext)
   at System.Windows.Application.LoadComponent(Uri resourceLocator, Boolean bSkipJournaledProperties)
   at System.Windows.Application.LoadComponent(Uri resourceLocator)
   at ReproAttachedPropertyCore30.CSharp.Fail.App.Main(String[] args) in C:\Users\maxim\Downloads\ReproWithBasicProperty\ReproAttachedPropertyCore30.CSharp.Fail\App.cs:line 18

  This exception was originally thrown at this call stack:
    [External Code]

Inner Exception 1:
XamlObjectWriterException: 'Cannot set unknown member '{clr-namespace:ReproAttachedPropertyCore30.CSharp.Fail}DummyAttached.Foo'.' Line number '11' and line position '6'.

Expected behavior: The resource to be loaded correctly, without throwing exceptions. Minimal repro: ReproWithBasicProperty.zip

JosephGarrone commented 3 years ago

Can confirm this is happening in .NET 4.8, consistently when trying to set either Triggers or Behaviors on a DataGrid. I'm wondering if this is caused by the fact that both Triggers and Behaviors (Their properties in Interaction.cs), are private or the fact that the name supplied to them is ShadowTriggers and ShadowBehaviors? I've only just started looking into this as it is a major blocker.

mwpowellhtx commented 1 week ago

Experiencing similar issues; unable to load class, where my attached property is declared, etc. From the same assembly, as at least one other issue, temporary projects, etc, have supposedly addressed.

At least in my case, I really am loathe to introduce yet another project to salve the issue, which is leading to somewhat of a wide footprint 3P dependencies, albeit somewhat mission critical, i.e. SkiaSharp, SKElement (WPF views), etc, as the error is already in kind of a building block layer to begin with, in the overall solution scheme of things.