Question

While exploring DI/IOC with Unity with WPF, I came across a question and need your feedback. Please consider the following scenario...

================================================================

public interface IDataServices
{
   string GetData();
}

================================================================

public class CopyTextDataServices : IDataServices
{
   public string GetData()
   {
      return "copy text from CopyTextDataServices";
   }
}

================================================================

public class TextDataServices : IDataServices
{
   public string GetData()
   {
      return "I am injected by setter property injection";
   }
}

================================================================

public interface ITextViewModel
{
   string LabelContnet { get; set; }
}

================================================================

public class TextViewModel : ITextViewModel
{
        public TextViewModel()
        {
            LabelContnet = "This is from view model";
        }

        public string LabelContnet { get; set; }
}

================================================================

public partial class MainWindow : Window
{
    public MainWindow(ITextViewModel textViewModel)
    {
        InitializeComponent();
        Loaded += MainWindow_Loaded;
        DataContext = textViewModel;
    }

    [Dependency]
    public IDataServices Services { get; set; }

    containing the event data.</param>
    private void MainWindow_Loaded(object sender, RoutedEventArgs e)
    {
        LabelLeft.Content = Services.GetData();
    }
}

================================================================

public partial class App : Application
{
    protected override void OnStartup(StartupEventArgs e)
    {
        base.OnStartup(e);

        IUnityContainer container = new UnityContainer();

        container.RegisterType<IDataServices, TextDataServices>();
        container.RegisterType<IDataServices, CopyTextDataServices>();
        container.RegisterType<ITextViewModel, TextViewModel>();

        var window = container.Resolve<MainWindow>();
        window.Show();
    }
}

================================================================

   <Window x:Class="TestAppWPF.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="MainWindow" Height="350" Width="525" FontSize="20">
    <StackPanel>
        <Label Content="{Binding Path=LabelContnet,FallbackValue=Left}" HorizontalAlignment="Left" Name="LabelLeft" />
        <Label Content="{Binding Path=LabelContnet,FallbackValue=Right}" HorizontalAlignment="Left" Name="LabelRight" />
    </StackPanel>
   </Window>

===================================================================

Now the result of this appears in the labels is

copy text from CopyTextDataServices This is from view model

But I want to know if I want to get data from TextDataServices, how can I do that?

Was it helpful?

Solution

The problem is in this line:

container.RegisterType<IDataServices, TextDataServices>();

// This overwrites the previous mapping.
// All dependencies to IDataServices will use CopyTextDataServices.
container.RegisterType<IDataServices, CopyTextDataServices>(); 

If you want to have both IDataServices, you'll need to register one or both as named instances.

container.RegisterType<IDataServices, TextDataServices>("TextDataServicesName");
container.RegisterType<IDataServices, CopyTextDataServices>("CopyTextDataServicesName"); 

In your control:

[Dependency("TextDataServicesName")]
public IDataServices Services { get; set; }
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top