Ed Noepel

Lets say I have a WPF Control named "FooViewer" which has a static property named "FooList". This property is static because anywhere I make a FooViewer in my app, I want it to share the FooList. I want to bind my FooList to a ListBox and have it update in realtime. So, I create a dependency property and point my wrapper property to this dependency property.

public static ObservableCollection<Foo> FooList
{
get
{
return (ObservableCollection<Foo>)GetValue(FooListProperty);
}
set
{
SetValue(FooListProperty, value);
}
}

public static readonly DependencyProperty FooListProperty =
DependencyProperty.Register("FooList", typeof(ObservableCollection<Foo>), typeof(FooViewer));



Now the get and set accessors of my FooList property will obviously fail, because it needs a reference to the Control to call GetValue or SetValue from. How can I get/set the dependency property from a static method



Re: Windows Presentation Foundation (WPF) Wrapping a DependencyProperty with a static property

Ed Noepel

After playing around with this a bit, I convinced myself that the DependencyProperty does not manage its data in a static fashion. It seems that a reference to an instance of Control is needed to Get or Set it. More importantly, data is bound to the particular instance of Control that called SetValue(...).

I figured I could split out my control into two controls: one with stuff that is unique per-instance, and another static class that encapsulates all the shared stuff. Unfortunately, I discovered static classes cannot derive from Control.

Is there a preferred pattern/practice to binding static data




Re: Windows Presentation Foundation (WPF) Wrapping a DependencyProperty with a static property

Adam Smith - MSFT

You're correct - DependencyProperty state is per instance, though being able to set static values for DPs sounds interesting as a feature.

Do you want a singleton source for a databinding or a singleton destination for databinding, or both






Re: Windows Presentation Foundation (WPF) Wrapping a DependencyProperty with a static property

Ed Noepel

I would like a singleton source. But since dependency properties keep a reference to the data, I suppose I would need a singleton destination as well. It seems with the existing implementation, a singleton destination is not achievable. Is there some way of defining a singleton source

I attempted making my class a singleton, but the XAML complained about instantiating a Control without a public ctor.




Re: Windows Presentation Foundation (WPF) Wrapping a DependencyProperty with a static property

Adam Smith - MSFT

(Note that this post has "x: Static" with a space, because without it, it shows up as xTongue Tiedtatic... the space shouldn't be there...)

I'm not really sure what a singleton Control would do, since it could only exist in one place in the tree. If you're simply looking for "an object which can have DependencyProperties", consider deriving directly from DependencyObject, or, if you would like change notifications and the ability to Freeze (become immutable and free threaded), and animate the properties, derive from Animatable (which derives from Freezable).

You won't be able to create a singleton in markup, because a XAML tag such as <my:FooBarClass .../> means "instantiate a new instance of my:FooBarClass", which you don't want. You can, however, use the {x: Static markup extension to retrieve the singleton from a static property on the type.

If the type is:

public class FooBarClass

{

public static FooBarClass SingletonInstance { get; }

...

}

you can grab this like so:

<Button DataContext="{x: Static my:FooBarClass.SingletonInstance}" .../>

or

<x: Static Member="my:FooBarClass.SingletonInstance" ... />

So you can then use this with a Binding, etc.

Here's some more info on this: http://msdn2.microsoft.com/en-us/library/ms742135.aspx






Re: Windows Presentation Foundation (WPF) Wrapping a DependencyProperty with a static property

Ed Noepel

Nice. So in my type, I exposed a static property (not a DP) named StaticFooList, which provides an ObservableCollection<Foo>. I then updated my XAML to (without the space trailing xSmile:

DataContext="{x: Static Member=local:FooBarClass.StaticFooList}"

At runtime, when Control.OnInitialized gets called in FooBarClass, I get the following error:
"Cannot convert the value in attribute 'DataContext' to object of type 'System.Windows.Markup.StaticExtension'. Error at object 'System.Windows.Controls.ControlTemplate', Line 26 Position 33."

The same happened when I tried binding the ItemSource attribute (its a ListBox). The web offered no suggestions as to what caused the problem. I played around binding it to other static properties of various data types. Simple things like strings did not produce the error. However for a listbox, binding the ItemsCollection to a string is not very useful.

Is there a way to get this to work with a collection




Re: Windows Presentation Foundation (WPF) Wrapping a DependencyProperty with a static property

Adam Smith - MSFT

(crossing fingers) Any chance there's an inner exception when you see that that will help explain why the StaticExtension is failing to parse




Re: Windows Presentation Foundation (WPF) Wrapping a DependencyProperty with a static property

Ed Noepel

I wish...InnerException is null.




Re: Windows Presentation Foundation (WPF) Wrapping a DependencyProperty with a static property

Ed Noepel

As a workaround, I moved my static data out of my FooBarClass Control and into its own non-static class. This non-static class simply contains a public static property that refers to a private static ObservableCollection<Foo>. The one-way databinding into my ListBox works nicely this way. I still wish I could keep this static data within the Control.