I need to create a control with few inputs / output with lots of internal functionality. I think the best approach is to create Dependency Properties for interaction with other application parts and have a private view model with hidden functions.
Here is my sample:
Window
<Window x:Class="WpfApplication1.MainWindow"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:app="clr-namespace:WpfApplication1">
<StackPanel>
    <DatePicker x:Name="DatePicker" />
    <app:MyControl DateCtrl="{Binding ElementName=DatePicker, Path=SelectedDate}" />
</StackPanel>
</Window>
MyControl
<UserControl x:Class="WpfApplication1.MyControl"
         xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
         xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
         xmlns:app="clr-namespace:WpfApplication1">
<UserControl.DataContext>
    <app:ViewModel />
</UserControl.DataContext>
<Grid>
        <TextBlock Text="{Binding DateVM}" />
</Grid>
</UserControl>
Control code-behind
using System;
using System.Windows;
namespace WpfApplication1
{
public partial class MyControl
{
    public MyControl()
    {
        InitializeComponent();
    }
    public static DependencyProperty DateCtrlProperty = DependencyProperty.Register("DateCtrl", typeof(DateTime), typeof(MyControl));
    public DateTime DateCtrl
    {
        get { return (DateTime) GetValue(DateCtrlProperty); }
        set { SetValue(DateCtrlProperty, value); }
    }
}
}
ViewModel
using System;
using System.ComponentModel;
namespace WpfApplication1
{
    public class ViewModel : INotifyPropertyChanged
    {
        private DateTime _dateVM;
        public DateTime DateVM
        {
            get { return _dateVM; }
            set
            {
                _dateVM = value;
                OnPropertyChanged("DateVM");
            }
        }
        public event PropertyChangedEventHandler PropertyChanged;
        protected virtual void OnPropertyChanged(string propertyName)
        {
            var handler = PropertyChanged;
            if (handler != null) handler(this, new PropertyChangedEventArgs(propertyName));
        }
    }
}
I need to achieve is to propagate date chosen in DatePicker down to MyControl's view model. Alternatively, is there any better pattern to use?
                        
What you describe is a common misconception that all views should have a view model. However, it is usually far simpler (and more appropriate) for
UserControls that are used as controls to simply use their ownDependencyPropertys.The problem with your method is that you have assigned the
UserControl DataContextinternally, so it cannot be set from outside the control. The solution is to not set theDataContextinternally, but instead to use aRelativeSource Bindingto access theUserControl DependencyPropertys like this:If you really have to use an internal view model, then declare a
DependencyPropertyof that type and data bind to it in the same way that I showed above: