diff --git a/.vscode/settings.json b/.vscode/settings.json new file mode 100644 index 0000000..a8c2003 --- /dev/null +++ b/.vscode/settings.json @@ -0,0 +1,5 @@ +{ + "python-envs.defaultEnvManager": "ms-python.python:conda", + "python-envs.defaultPackageManager": "ms-python.python:conda", + "python-envs.pythonProjects": [] +} \ No newline at end of file diff --git a/App.xaml.cs b/App.xaml.cs index e874970..48b8709 100644 --- a/App.xaml.cs +++ b/App.xaml.cs @@ -1,4 +1,4 @@ -using System.Configuration; +using System.Configuration; using System.Data; using System.Windows; @@ -7,7 +7,7 @@ namespace CopyRou /// /// Interaction logic for App.xaml /// - public partial class App : Application + public partial class App : System.Windows.Application { } diff --git a/AppConfig.cs b/AppConfig.cs new file mode 100644 index 0000000..0703a93 --- /dev/null +++ b/AppConfig.cs @@ -0,0 +1,83 @@ +using System; +using System.Collections.Generic; +using System.IO; +using System.Text.Json; + +namespace CopyRou +{ + public class AppConfig + { + public List SourcePaths { get; set; } = new(); + public string DestPath { get; set; } = string.Empty; + + private static readonly string ConfigPath = Path.Combine( + Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData), + "CopyRou", "config.json"); + + public static AppConfig Load() + { + try + { + if (File.Exists(ConfigPath)) + { + var json = File.ReadAllText(ConfigPath); + return JsonSerializer.Deserialize(json) ?? new AppConfig(); + } + } + catch (Exception ex) + { + // 如果加载失败,返回默认配置 + System.Diagnostics.Debug.WriteLine($"加载配置失败: {ex.Message}"); + } + + return new AppConfig + { + SourcePaths = new List + { + @"Z:\Routing\A1-ROUTING\NEW-ROUTING", + @"Z:\Routing\A2-ROUTING\NEW-ROUTING" + }, + DestPath = @"D:\ARPTWork\rou" + }; + } + + public void Save() + { + try + { + var directory = Path.GetDirectoryName(ConfigPath); + if (!string.IsNullOrEmpty(directory) && !Directory.Exists(directory)) + Directory.CreateDirectory(directory); + + var json = JsonSerializer.Serialize(this, new JsonSerializerOptions { WriteIndented = true }); + File.WriteAllText(ConfigPath, json); + } + catch (Exception ex) + { + System.Diagnostics.Debug.WriteLine($"保存配置失败: {ex.Message}"); + } + } + + public string GetSourcePathsText() + { + return string.Join(Environment.NewLine, SourcePaths); + } + + public void SetSourcePathsFromText(string text) + { + SourcePaths.Clear(); + if (!string.IsNullOrWhiteSpace(text)) + { + var paths = text.Split(new[] { Environment.NewLine, "\n", "\r" }, StringSplitOptions.RemoveEmptyEntries); + foreach (var path in paths) + { + var trimmedPath = path.Trim(); + if (!string.IsNullOrEmpty(trimmedPath)) + { + SourcePaths.Add(trimmedPath); + } + } + } + } + } +} \ No newline at end of file diff --git a/CopyRou.csproj b/CopyRou.csproj index f01bf10..efbaa4d 100644 --- a/CopyRou.csproj +++ b/CopyRou.csproj @@ -1,4 +1,4 @@ - + WinExe @@ -6,6 +6,7 @@ enable enable true + true AnyCPU;x86 diff --git a/FileService.cs b/FileService.cs new file mode 100644 index 0000000..9f965ec --- /dev/null +++ b/FileService.cs @@ -0,0 +1,151 @@ +using System; +using System.Collections.Generic; +using System.IO; +using System.Linq; +using System.Threading.Tasks; + +namespace CopyRou +{ + public class FileService : IFileService + { + public bool MatchFolderName(string folderName, string numPart, string versionPart) + { + if (string.IsNullOrEmpty(folderName) || + string.IsNullOrEmpty(numPart) || + string.IsNullOrEmpty(versionPart)) + return false; + + var folderNameLower = folderName.ToLower(); + var numLength = numPart.Length; + + // 检查文件夹名长度是否足够 + if (folderNameLower.Length < 3 + numLength) + return false; + + // 从第4个字符开始匹配数字编号(索引3) + var numInName = folderNameLower.Substring(3, numLength); + if (numInName != numPart.ToLower()) + return false; + + // 检查版本部分 + var versionInName = folderNameLower.Substring(3 + numLength); + return versionInName.StartsWith(versionPart.ToLower()); + } + + public List CopyRouFiles(string sourceFolder, string number, string destPath, ILogger logger) + { + var copiedFiles = new List(); + var edFoldersFound = 0; + var rouExtensions = new[] { ".rou", ".rou1", ".rou2", ".rou3" }; + + try + { + // 确保目标目录存在 + Directory.CreateDirectory(destPath); + + foreach (var item in Directory.GetDirectories(sourceFolder)) + { + var folderName = Path.GetFileName(item); + if (folderName.StartsWith("ED", StringComparison.OrdinalIgnoreCase) || + folderName.StartsWith("ROU", StringComparison.OrdinalIgnoreCase)) + { + edFoldersFound++; + logger?.Log($"正在处理ED文件夹: {folderName}"); + + // 递归查找所有.rou文件 + var rouFiles = Directory.GetFiles(item, "*.*", SearchOption.AllDirectories) + .Where(file => rouExtensions.Contains(Path.GetExtension(file).ToLower())) + .ToList(); + + foreach (var srcFile in rouFiles) + { + var fileName = Path.GetFileName(srcFile); + var baseName = $"{number}_{folderName}_{fileName}"; + var destFile = Path.Combine(destPath, baseName); + + File.Copy(srcFile, destFile, true); + copiedFiles.Add(baseName); + } + } + } + + if (edFoldersFound == 0) + { + logger?.LogWarning("未找到任何以ED或ROU开头的文件夹"); + } + else if (!copiedFiles.Any()) + { + logger?.LogWarning("在ED文件夹中未找到任何.rou系列文件"); + } + else + { + logger?.Log($"成功从 {edFoldersFound} 个ED文件夹复制 {copiedFiles.Count} 个文件"); + } + } + catch (Exception ex) + { + logger?.LogError($"复制文件时发生错误: {ex.Message}"); + } + + return copiedFiles; + } + + public async Task ProcessCodes(List codes, List sourcePaths, string destPath, + IProgress progress, ILogger logger) + { + var totalCodes = codes.Count; + var processedCodes = 0; + + foreach (var code in codes) + { + var trimmedCode = code.Trim(); + if (string.IsNullOrEmpty(trimmedCode)) + continue; + + logger?.Log($"\n处理编号: {trimmedCode}"); + + var numPart = trimmedCode.Length >= 5 ? trimmedCode.Substring(0, 5) : trimmedCode; + var versionPart = trimmedCode.Length > 5 ? trimmedCode.Substring(5) : ""; + + var found = false; + + foreach (var sourceRoot in sourcePaths) + { + var numFolder = Path.Combine(sourceRoot, numPart); + if (!Directory.Exists(numFolder)) + continue; + + try + { + var folders = Directory.GetDirectories(numFolder); + foreach (var folder in folders) + { + var folderName = Path.GetFileName(folder); + if (MatchFolderName(folderName, numPart, versionPart)) + { + logger?.Log($"找到匹配文件夹: {folder}"); + CopyRouFiles(folder, numPart, destPath, logger ?? new Logger()); + found = true; + } + } + } + catch (Exception ex) + { + logger?.LogError($"访问文件夹 {numFolder} 时发生错误: {ex.Message}"); + } + } + + if (!found) + { + logger?.Log("未找到匹配的文件夹"); + } + + processedCodes++; + progress?.Report((int)((double)processedCodes / totalCodes * 100)); + + // 添加小延迟以避免UI阻塞 + await Task.Delay(10); + } + } + } +} \ No newline at end of file diff --git a/IFileService.cs b/IFileService.cs new file mode 100644 index 0000000..f9bc87e --- /dev/null +++ b/IFileService.cs @@ -0,0 +1,12 @@ +using System.Collections.Generic; +using System.Threading.Tasks; + +namespace CopyRou +{ + public interface IFileService + { + bool MatchFolderName(string folderName, string numPart, string versionPart); + List CopyRouFiles(string sourceFolder, string number, string destPath, ILogger logger); + Task ProcessCodes(List codes, List sourcePaths, string destPath, IProgress progress, ILogger logger); + } +} \ No newline at end of file diff --git a/ILogger.cs b/ILogger.cs new file mode 100644 index 0000000..e2c730a --- /dev/null +++ b/ILogger.cs @@ -0,0 +1,11 @@ +namespace CopyRou +{ + public interface ILogger + { + void Log(string message); + void LogError(string message); + void LogWarning(string message); + void Clear(); + event System.EventHandler? MessageLogged; + } +} \ No newline at end of file diff --git a/Logger.cs b/Logger.cs new file mode 100644 index 0000000..44fb54d --- /dev/null +++ b/Logger.cs @@ -0,0 +1,32 @@ +using System; + +namespace CopyRou +{ + public class Logger : ILogger + { + public event EventHandler? MessageLogged; + + public void Log(string message) + { + var timestampedMessage = $"[{DateTime.Now:HH:mm:ss}] {message}"; + MessageLogged?.Invoke(this, timestampedMessage); + } + + public void LogError(string message) + { + var timestampedMessage = $"[{DateTime.Now:HH:mm:ss}] [错误] {message}"; + MessageLogged?.Invoke(this, timestampedMessage); + } + + public void LogWarning(string message) + { + var timestampedMessage = $"[{DateTime.Now:HH:mm:ss}] [警告] {message}"; + MessageLogged?.Invoke(this, timestampedMessage); + } + + public void Clear() + { + MessageLogged?.Invoke(this, "[LOG CLEARED]"); + } + } +} \ No newline at end of file diff --git a/MainWindow.xaml b/MainWindow.xaml index 4a33dc9..354a9c2 100644 --- a/MainWindow.xaml +++ b/MainWindow.xaml @@ -1,12 +1,215 @@ - - + + + + + + + + + + + + + + + + + + + + + + + +