Utilities for WPF applications, including:
DelegateCommandfor synchronous and asynchronous commands- Enum markup extensions (
EnumValuesExtension,LocalizedEnumValuesExtension) BooleanToValueConverterfor flexible bool-to-value conversion in bindings- Dispatcher helpers (
SwitchToDispatcherThread)
dotnet add package Meziantou.Framework.WPFusing Meziantou.Framework.WPF;
public sealed class SampleViewModel
{
public IDelegateCommand SaveCommand { get; } = DelegateCommand.Create(
execute: () => Console.WriteLine("Saved"),
canExecute: () => true);
}ConcurrentObservableCollection<T> has moved to the Meziantou.Framework.Threading package,
where it is bound to a SynchronizationContext instead of a WPF Dispatcher. Creating it on the UI thread keeps the previous behavior:
dotnet add package Meziantou.Framework.Threadingusing Meziantou.Framework.Collections.Concurrent;
var collection = new ConcurrentObservableCollection<string>();
listBox.ItemsSource = collection.AsObservable;
await Task.Run(() => collection.Add("Item from background thread"));Meziantou.Framework.WPF.Collections.ConcurrentObservableCollection<T> no longer exists. Add a reference to the
Meziantou.Framework.Threading package and update the using directive.
<Window
xmlns:wpf="clr-namespace:Meziantou.Framework.WPF;assembly=Meziantou.Framework.WPF">
<ComboBox
ItemsSource="{wpf:LocalizedEnumValues {x:Type local:MyEnum}}"
DisplayMemberPath="Name"
SelectedValuePath="Value" />
</Window><Window.Resources>
<wpf:BooleanToValueConverter
x:Key="BoolToVisibility"
TrueValue="{x:Static Visibility.Visible}"
FalseValue="{x:Static Visibility.Collapsed}" />
</Window.Resources>