.net WPF应用程序第一次加载带有窗口的插件,但第二次无法显示窗口

gpnt7bae  于 2023-11-20  发布在  .NET
关注(0)|答案(1)|浏览(222)

该应用程序通过加载程序集来实现插件。插件可以多次加载,并且它的工作非常简单,直到我从插件中显示一个窗口。它第一次工作,但第二次不会打开窗口。

示例

主机应用

Host.csproj

  1. <Project Sdk="Microsoft.NET.Sdk">
  2. <PropertyGroup>
  3. <LangVersion>default</LangVersion>
  4. <TargetFramework>net48</TargetFramework>
  5. <OutputType>WinExe</OutputType>
  6. <UseWPF>true</UseWPF>
  7. <StartupObject>Host.MainModule</StartupObject>
  8. <DebugType>full</DebugType>
  9. <DebugSymbols>true</DebugSymbols>
  10. </PropertyGroup>
  11. <ItemGroup>
  12. <ApplicationDefinition Include="MainModule.xaml">
  13. <Generator>MSBuild:Compile</Generator>
  14. <SubType>Designer</SubType>
  15. </ApplicationDefinition>
  16. </ItemGroup>
  17. </Project>

字符串
MainModule.xaml

  1. <Application x:Class="Host.MainModule"
  2. xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
  3. xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"/>


MainModule.xaml.cs

  1. using System;
  2. using System.IO;
  3. using System.Reflection;
  4. using System.Windows;
  5. namespace Host;
  6. public partial class MainModule
  7. {
  8. protected override void OnStartup(StartupEventArgs e)
  9. {
  10. base.OnStartup(e);
  11. LoadAndRun(@"..\..\..\..\..\Service\bin\x64\Debug\net48\Service.dll");
  12. LoadAndRun(@"..\..\..\..\..\Service\bin\x64\Debug\net48\Service.dll");
  13. MessageBox.Show("ok");
  14. Shutdown();
  15. }
  16. private static void LoadAndRun(string path) {
  17. var folder = Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location);
  18. var assembly = Assembly.LoadFile(Path.GetFullPath(Path.Combine(folder, path)));
  19. var provider = assembly.GetType("Service.Provider");
  20. var instance = Activator.CreateInstance(provider);
  21. var method = provider.GetMethod("Run");
  22. method.Invoke(instance, null);
  23. }
  24. }

服务库

Service.csproj

  1. <Project Sdk="Microsoft.NET.Sdk">
  2. <PropertyGroup>
  3. <LangVersion>default</LangVersion>
  4. <TargetFramework>net48</TargetFramework>
  5. <OutputType>library</OutputType>
  6. <UseWPF>true</UseWPF>
  7. <DebugType>full</DebugType>
  8. <DebugSymbols>true</DebugSymbols>
  9. <DefineConstants>TRACE</DefineConstants>
  10. </PropertyGroup>
  11. </Project>


Provider.cs

  1. using System;
  2. using System.Diagnostics;
  3. using Microsoft.SqlServer.Server;
  4. namespace Service;
  5. public sealed class Provider {
  6. public void Run() {
  7. var form = new Form();
  8. var sw = Stopwatch.StartNew();
  9. form.ShowDialog();
  10. Console.WriteLine($"{nameof(Provider)}.{nameof(Run)}: form was opened for {sw.ElapsedMilliseconds} ms");
  11. }
  12. }


Form.xaml

  1. <Window x:Class="Service.Form"
  2. xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
  3. xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
  4. Title="Form"
  5. Height="400" Width="200">
  6. </Window>


Form.xaml.cs

  1. using System;
  2. namespace Service;
  3. public partial class Form {
  4. public Form() {
  5. Console.WriteLine($"{nameof(Form)}.{nameof(Form)}: start");
  6. InitializeComponent();
  7. Console.WriteLine($"{nameof(Form)}.{nameof(Form)}: done");
  8. }
  9. }

运行

启动时,应用程序显示一次窗体,然后显示一个消息框。
控制台输出为:

  1. Form.Form: start
  2. Form.Form: done
  3. Provider.Run: form was opened for 1159 ms
  4. Form.Form: start
  5. Form.Form: done
  6. Provider.Run: form was opened for 0 ms


正如您所看到的,表单第二次启动,没有例外,但立即关闭。
我将感谢你在这件事上的帮助。谢谢!

rta7y2nd

rta7y2nd1#

选中Application.ShutdownMode。默认值为OnLastWindowClose,因此应用程序将在第一个窗口关闭时关闭。如果您想保持应用程序运行,请将其更改为OnExplicitWindow。
它与从单独的程序集加载Window无关。

相关问题