Skip to content

Instantly share code, notes, and snippets.

@sajidmohammed88
Last active April 13, 2024 20:40
Show Gist options
  • Star 13 You must be signed in to star a gist
  • Fork 6 You must be signed in to fork a gist
  • Save sajidmohammed88/99928bbb3e94028fc6be175d67c0b46f to your computer and use it in GitHub Desktop.
Save sajidmohammed88/99928bbb3e94028fc6be175d67c0b46f to your computer and use it in GitHub Desktop.
Dependency injection in WPF project with .net core

Dependency injection in WPF project with .net core

Delete StartupUri="MainWindow.xaml" from App.xaml
Install packages :
Microsoft.Extensions.Configuration.Json
Microsoft.Extensions.DependencyInjection
Microsoft.Extensions.Options.ConfigurationExtensions
Add the file appsettings.json in the root of the project to use it for configuration.
Override OnStartup method in App.Xaml.Cs class :
public IServiceProvider ServiceProvider { get; private set; }

public IConfiguration Configuration { get; private set; }

protected override void OnStartup(StartupEventArgs e)
{
    var builder = new ConfigurationBuilder()
     .SetBasePath(Directory.GetCurrentDirectory())
     .AddJsonFile("appsettings.json", optional: false, reloadOnChange: true);

    Configuration = builder.Build();

    var serviceCollection = new ServiceCollection();
    ConfigureServices(serviceCollection);

    ServiceProvider = serviceCollection.BuildServiceProvider();

    var mainWindow = ServiceProvider.GetRequiredService<MainWindow>();
    mainWindow.Show();
}

private void ConfigureServices(IServiceCollection services)
{
    services.Configure<AppSettings>(Configuration.GetSection(nameof(AppSettings)));

    services.AddTransient(typeof(MainWindow));
}
@Montago
Copy link

Montago commented Oct 28, 2023

Nice ..

How do i then fetch my services in various usercontrols ? :)

eg, if the service isn't injected via constructor, then how do you fetch it ?

i'm guessing something a like: ServiceProvider.Current.GetInstance();

but ServiceProvider isn't globally available ?

@Montago
Copy link

Montago commented Oct 29, 2023

so, here's what i've done so far:

make the ServiceProvider Static on App:

    public static IServiceProvider ServiceProvider { get; private set; }

Access it via App class:

    App.ServiceProvider.GetService<...>

havent tested if it works :D

@MojoFilter
Copy link

MojoFilter commented Apr 13, 2024

so, here's what i've done so far:

make the ServiceProvider Static on App:

    public static IServiceProvider ServiceProvider { get; private set; }

Access it via App class:

    App.ServiceProvider.GetService<...>

havent tested if it works :D

That is a way to do it, but you're shooting yourself in the foot a little bit if you're doing anything serious. That's because instead of abstracting dependencies, you now have a dependency on that service provider.

It's a lot nicer when your actual UI parts like user controls don't need to know about services at all, rather they provide a rendering of the underlying data (or viewmodel if you're fancy). It's that underlying little bean that needs to know how to talk to services. But the actual wpf parts can remain blissfully unconcerned.

If the MainWindow constructor requires all of the services and factories needed to pass down to all the data parts, it can stay pretty clean.

Typically when you're doing it this way, though, the only parameter for MainWindow would be an IMainWindowViewModel or something similar and in the implementation of that is where it goes hog wild with dependency requirements.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment