diff --git a/XplorePlane/ViewModels/Main/LibraryVersionsViewModel.cs b/XplorePlane/ViewModels/Main/LibraryVersionsViewModel.cs new file mode 100644 index 0000000..843678b --- /dev/null +++ b/XplorePlane/ViewModels/Main/LibraryVersionsViewModel.cs @@ -0,0 +1,170 @@ +using System; +using Prism.Mvvm; +using System.Collections.ObjectModel; +using System.Diagnostics; +using System.IO; +using System.Reflection; + +namespace XplorePlane.ViewModels +{ + public class LibraryVersionItem : BindableBase + { + public string Category { get; set; } = ""; + public string Name { get; set; } = ""; + public string Version { get; set; } = ""; + public string Path { get; set; } = ""; + } + + public class LibraryVersionsViewModel : BindableBase + { + public ObservableCollection Libraries { get; } = new(); + + public string AppVersion { get; } + + public LibraryVersionsViewModel() + { + var appAsm = Assembly.GetEntryAssembly(); + AppVersion = appAsm?.GetName().Version?.ToString() ?? "未知"; + + LoadLibraryVersions(); + } + + private void LoadLibraryVersions() + { + AddAssemblyInfo("通信/公共库", "XP.Common"); + AddAssemblyInfo("通信/公共库", "BR.AN.PviServices"); + AddAssemblyInfo("通信/公共库", "Prism.DryIoc"); + AddAssemblyInfo("通信/公共库", "Prism"); + AddAssemblyInfo("通信/公共库", "DryIoc"); + AddAssemblyInfo("通信/公共库", "Serilog"); + AddAssemblyInfo("通信/公共库", "System.Data.SQLite"); + AddAssemblyInfo("通信/公共库", "Microsoft.Data.Sqlite"); + + AddAssemblyInfo("图像处理库", "Emgu.CV"); + AddAssemblyInfo("图像处理库", "Emgu.CV.Bitmap"); + AddAssemblyInfo("图像处理库", "Microsoft.ML.OnnxRuntime"); + AddAssemblyInfo("图像处理库", "XP.ImageProcessing.Core"); + AddAssemblyInfo("图像处理库", "XP.ImageProcessing.Processors"); + AddAssemblyInfo("图像处理库", "XP.ImageProcessing.CfgControl"); + AddAssemblyInfo("图像处理库", "XP.ImageProcessing.RoiControl"); + + AddAssemblyInfo("相机库", "Basler.Pylon"); + AddAssemblyInfo("相机库", "XP.Camera"); + + AddAssemblyInfo("UI 框架", "Fluent"); + AddAssemblyInfo("UI 框架", "Telerik.Windows.Controls"); + AddAssemblyInfo("UI 框架", "Telerik.Windows.Controls.GridView"); + AddAssemblyInfo("UI 框架", "Telerik.Windows.Controls.Chart"); + AddAssemblyInfo("UI 框架", "Telerik.Windows.Controls.Docking"); + AddAssemblyInfo("UI 框架", "MahApps.Metro"); + + AddAssemblyInfo("硬件库", "XP.Hardware.RaySource"); + AddAssemblyInfo("运行时", "System.Runtime", useLoaded: true); + + AddOpenCvNativeVersion(); + } + + private void AddAssemblyInfo(string category, string assemblyName, bool useLoaded = false) + { + try + { + Assembly? asm = null; + + if (useLoaded) + { + foreach (var a in AppDomain.CurrentDomain.GetAssemblies()) + { + if (a.GetName().Name == assemblyName) + { + asm = a; + break; + } + } + } + else + { + foreach (var a in AppDomain.CurrentDomain.GetAssemblies()) + { + if (a.GetName().Name == assemblyName) + { + asm = a; + break; + } + } + + if (asm == null) + { + try + { + asm = Assembly.Load(assemblyName); + } + catch + { + } + } + } + + if (asm != null) + { + var name = asm.GetName(); + var fileVersion = FileVersionInfo.GetVersionInfo(asm.Location); + + Libraries.Add(new LibraryVersionItem + { + Category = category, + Name = name.Name ?? assemblyName, + Version = fileVersion.FileVersion ?? name.Version?.ToString() ?? "未知", + Path = asm.Location + }); + } + else + { + Libraries.Add(new LibraryVersionItem + { + Category = category, + Name = assemblyName, + Version = "未加载", + Path = "" + }); + } + } + catch + { + Libraries.Add(new LibraryVersionItem + { + Category = category, + Name = assemblyName, + Version = "读取失败", + Path = "" + }); + } + } + + private void AddOpenCvNativeVersion() + { + try + { + var baseDir = AppDomain.CurrentDomain.BaseDirectory; + var versionFile = Path.Combine(baseDir, "version_string.inc"); + if (File.Exists(versionFile)) + { + var content = File.ReadAllText(versionFile); + var match = System.Text.RegularExpressions.Regex.Match(content, @"OpenCV\s+([\d.]+)"); + if (match.Success) + { + Libraries.Add(new LibraryVersionItem + { + Category = "图像处理库", + Name = "OpenCV (Native/cvextern)", + Version = match.Groups[1].Value, + Path = Path.Combine(baseDir, "cvextern.dll") + }); + } + } + } + catch + { + } + } + } +} diff --git a/XplorePlane/Views/Main/LibraryVersionsView.xaml b/XplorePlane/Views/Main/LibraryVersionsView.xaml new file mode 100644 index 0000000..9d0c989 --- /dev/null +++ b/XplorePlane/Views/Main/LibraryVersionsView.xaml @@ -0,0 +1,82 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/XplorePlane/Views/Main/LibraryVersionsView.xaml.cs b/XplorePlane/Views/Main/LibraryVersionsView.xaml.cs new file mode 100644 index 0000000..44288ea --- /dev/null +++ b/XplorePlane/Views/Main/LibraryVersionsView.xaml.cs @@ -0,0 +1,27 @@ +using System.Windows; +using System.Windows.Controls; +using System.Windows.Data; +using XplorePlane.ViewModels; + +namespace XplorePlane.Views +{ + public partial class LibraryVersionsView : UserControl + { + public LibraryVersionsView() + { + InitializeComponent(); + + Loaded += (s, e) => + { + if (DataContext is LibraryVersionsViewModel vm) + { + var view = CollectionViewSource.GetDefaultView(vm.Libraries); + if (view.GroupDescriptions.Count == 0) + { + view.GroupDescriptions.Add(new PropertyGroupDescription("Category")); + } + } + }; + } + } +} \ No newline at end of file diff --git a/XplorePlane/Views/Main/LibraryVersionsWindow.xaml b/XplorePlane/Views/Main/LibraryVersionsWindow.xaml new file mode 100644 index 0000000..55347bd --- /dev/null +++ b/XplorePlane/Views/Main/LibraryVersionsWindow.xaml @@ -0,0 +1,96 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +