diff --git a/RustTools/Editor/EditorLoad.cs b/RustTools/Editor/EditorLoad.cs index 119403e..19947c9 100644 --- a/RustTools/Editor/EditorLoad.cs +++ b/RustTools/Editor/EditorLoad.cs @@ -1,101 +1,64 @@ using System.Collections.ObjectModel; +using System.Diagnostics; namespace RustTools.Editor; public class EditorLoad { /// - /// 加载所有的文件 Debug 用 + /// 获取目录下的文件和文件夹 /// - /// - /// - private void LoadDirectory(DirectoryInfo directoryInfo, ExplorerItem parentItem) + /// + /// + public static ObservableCollection GetData(string dir) { - // 获取当前目录中的所有子目录 - var directories = directoryInfo.GetDirectories(); - foreach (var directory in directories) - { - // 创建新的 ExplorerItem 代表当前子目录 - var folderItem = new ExplorerItem - { - Name = directory.Name, - Type = ExplorerItem.ExplorerItemType.Folder - }; - - // 将这个目录项添加到父级的 Children 集合中 - parentItem.Children.Add(folderItem); - - // 递归调用,继续加载子目录中的内容 - LoadDirectory(directory, folderItem); - } - - // 获取当前目录中的所有文件 - var files = directoryInfo.GetFiles(); - foreach (var file in files) - { - // 创建新的 ExplorerItem 代表当前文件 - var fileItem = new ExplorerItem - { - Name = file.Name, - Type = ExplorerItem.ExplorerItemType.File - }; - - // 将这个文件项添加到父级的 Children 集合中 - parentItem.Children.Add(fileItem); - } - } - - - public ObservableCollection GetData(string dir) - { - var list = new ObservableCollection(); - + var list = new ObservableCollection(); var directoryInfos = new DirectoryInfo(dir); - - // 创建根节点 ExplorerItem 根节点不显示防止用户删除 - //var rootItem = new ExplorerItem - //{ - // Name = directoryInfos.Name, - // Dir = directoryInfos.FullName, - // Type = ExplorerItem.ExplorerItemType.Folder, - //}; - //LoadDirectory(directoryInfos,rootItem); + //获取文件夹 foreach (var file in directoryInfos.GetDirectories()) { - var explorerItem = new ExplorerItem() + var explorerItem = new FileItem(true) { Name = file.Name, Dir = file.FullName, - Type = ExplorerItem.ExplorerItemType.Folder }; + //检测是否有子文件 + if (HasChildren(file.FullName)) + { + explorerItem.Children.Add(new FileItem()); + } list.Add(explorerItem); - foreach (var a in file.GetDirectories()) - { - explorerItem.Children.Add(new ExplorerItem() - { - Name = a.Name, - Dir = a.FullName, - Type = ExplorerItem.ExplorerItemType.Folder - }); - } - foreach (var a in file.GetFiles()) - { - explorerItem.Children.Add(new ExplorerItem() - { - Name = a.Name, - Dir = a.FullName, - Type = ExplorerItem.ExplorerItemType.File - }); - } } + //获取文件 foreach (var file in directoryInfos.GetFiles()) { - list.Add(new ExplorerItem() + list.Add(new FileItem() { Name = file.Name, Dir = file.FullName, - Type = ExplorerItem.ExplorerItemType.File + IsFolder = false, }); } return list; } + private static bool HasChildren(string path) + { + try + { + // 检查是否有子目录或子文件 + return Directory.EnumerateDirectories(path).Any() || Directory.EnumerateFiles(path).Any(); + } + catch (UnauthorizedAccessException) + { + // 捕获权限异常(例如无法访问某些系统文件夹) + return false; + } + catch (Exception ex) + { + Debug.WriteLine($"Error checking children for path {path}: {ex.Message}"); + return false; + } + } + + + } diff --git a/RustTools/Editor/EditorTreeView.cs b/RustTools/Editor/EditorTreeView.cs index 6a6baa1..45119ef 100644 --- a/RustTools/Editor/EditorTreeView.cs +++ b/RustTools/Editor/EditorTreeView.cs @@ -1,140 +1,108 @@  using System.Diagnostics; -using Microsoft.UI.Xaml; using Microsoft.UI.Xaml.Controls; -using Microsoft.UI.Xaml.Input; -using RustTools.muqing; -using Windows.ApplicationModel.DataTransfer; -using Windows.Storage; - namespace RustTools.Editor; public class EditorTreeView : TreeView { + public EditorTreeView() { - //CanDragItems = false; - //CanReorderItems =false; - //DragEnter += EditorTreeView_DragEnter; - DragItemsStarting += TreeView_DragItemsStarting; - DragItemsCompleted += EditorTreeView_DragItemsCompleted; - //DragOver += TreeView_DragOver; - //Drop += TreeView_Drop; - // 在构造函数中注册事件处理程序 - } - private void TreeView_DragItemsStarting(TreeView sender, TreeViewDragItemsStartingEventArgs e) - { - //gj.sc("TreeView_DragItemsStarting"+e); - var items = e.Items.Cast().ToList(); - var firstItem = items.First(); - gj.sc(firstItem.Dir); - e.Data.SetData("path", firstItem.Dir); - e.Data.RequestedOperation = DataPackageOperation.Move; // Use Copy to avoid moving items - } - private void EditorTreeView_DragItemsCompleted(TreeView sender, TreeViewDragItemsCompletedEventArgs e) - { + //点击事件 + this.ItemInvoked += TreeView_ItemInvoked; +// TreeView.Expanding +//当用户点击小箭头展开节点时触发。 - // 获取拖拽的项 - var items = e.Items.Cast().ToList(); +//TreeView.Collapsed +//当用户点击小箭头折叠节点时触发。 + this.Expanding += TreeView_Expanding; + this.Collapsed += TreeView_Collapsed; + } + private async void TreeView_ItemInvoked(TreeView sender, TreeViewItemInvokedEventArgs args) + { + // 获取触发点击的 TreeViewItem + var treeViewItem = sender.ContainerFromItem(args.InvokedItem) as TreeViewItem; - // 检查是否有至少一个项被放下 - if (items.Any()) + + if (args.InvokedItem is FileItem invokedItem) { - var firstItem = items.First(); // 获取第一个放下的项 - - // 输出放下项的信息 - Debug.WriteLine($"放下了 {firstItem.Dir}"); - } - } - - /// - /// 如果是shift则开启多选状态 - /// - /// - /// - private void treeView_KeyDown(object sender, KeyRoutedEventArgs e) - { - // 检查是否按下了Shift键 - if (e.Key == Windows.System.VirtualKey.Shift) - { - gj.sc(e.Key); - // 启用多选模式 - SelectionMode = TreeViewSelectionMode.Multiple; - } - } - private void treeView_KeyUp(object sender, KeyRoutedEventArgs e) - { - // 检查是否松开了Shift键 - if (e.Key == Windows.System.VirtualKey.Shift) - { // 清除当前多选模式下选中的项目 - var selectedItems = SelectedItems.ToList(); - foreach (var item in selectedItems) + if (invokedItem.IsFolder) { - SelectedItems.Remove(item); + //invokedItem.Children.Clear(); + //Debug.WriteLine($"Folder clicked: {invokedItem.Name}"); + //// 异步加载子项数据 + //var newChildren = await Task.Run(() => EditorLoad.GetData(invokedItem.Dir)); + //// 更新 Children 集合 + //foreach (var child in newChildren) + //{ + // invokedItem.Children.Add(child); + //} + //// 展开 TreeViewItem + //if (treeViewItem != null&&treeViewItem.IsExpanded==false) + //{ + // treeViewItem.IsExpanded = true; + //} } - gj.sc("取消"); - // 取消多选模式 - SelectionMode = TreeViewSelectionMode.Single; - //treeView.SelectedItems.Clear(); - } - } - - - - - - /// - /// 其他窗口的文件夹拖过来的例子 - /// - /// - /// - private void TreeView_DragOver(object sender, DragEventArgs e) - { - gj.sc(e); - // Allow dragging but prevent reordering - if (e.DataView.Contains(StandardDataFormats.StorageItems)) - { - e.AcceptedOperation = DataPackageOperation.Move; // Use Copy to avoid reordering - e.Handled = true; - } - } - /// - /// 其他文件夹拖过来的放下事件 - /// - /// - /// - private async void TreeView_Drop(object sender, DragEventArgs e) - { - gj.sc("TreeView_Drop: " + e); - // Handle drop event if needed but prevent reordering - if (e.DataView.Contains(StandardDataFormats.StorageItems)) - { - var storageItems = await e.DataView.GetStorageItemsAsync(); - - // 获取目标文件夹,即拖放的位置 - - // 获取目标位置 - var treeView = sender as TreeView; - - var data = await e.DataView.GetDataAsync("path"); - gj.sc(data); - foreach (var item in storageItems) + else { - if (item is StorageFolder folder) - { - // 移动文件夹 - gj.sc(folder.Path + "-->"); - //var newFolder = await folder.MoveAsync(targetFolder, folder.Name, NameCollisionOption.ReplaceExisting); - } - else if (item is StorageFile file) - { - // 移动文件 - //var newFile = await file.MoveAsync(targetFolder, file.Name, NameCollisionOption.ReplaceExisting); - } + Debug.WriteLine($"File clicked: {invokedItem.Name}"); } - - e.Handled = true; } } + + + // TreeView.Expanding 事件 + private async void TreeView_Expanding(TreeView sender, TreeViewExpandingEventArgs args) + { + if (args.Item is FileItem expandingItem) + { + Debug.WriteLine($"Expanding: {expandingItem.Name}"); + + // 如果需要动态加载子项(仅当没有加载过子项时) + if (expandingItem.IsFolder) + { + expandingItem.Children.Clear(); + var newChildren = await Task.Run(() => EditorLoad.GetData(expandingItem.Dir)); + // 更新 Children 集合 + foreach (var child in newChildren) + { + expandingItem.Children.Add(child); + } + Debug.WriteLine($"Loaded children for: {expandingItem.Name}"); + } + } + } + + // TreeView.Collapsed 事件 + private void TreeView_Collapsed(TreeView sender, TreeViewCollapsedEventArgs args) + { + if (args.Item is FileItem collapsedItem) + { + // 清空子节点集合 + if (collapsedItem.IsFolder && collapsedItem.Children != null) + { + // 设置当前项的所有子节点的 IsExpanded 为 false + //SetIsExpandedForChildren(collapsedItem, false); + Debug.WriteLine($"Children cleared for: {collapsedItem.Name}"); + } + // 处理折叠事件(例如,清理子项、节省资源等) + } + } + + // 递归设置子节点的 IsExpanded 为 false + private void SetIsExpandedForChildren(FileItem item, bool isExpanded) + { + foreach (var child in item.Children) + { + // 设置每个子项的 IsExpanded 状态 + child.IsExpanded = isExpanded; + + // 如果子项有子节点,递归处理 + if (child.IsFolder && child.Children.Count > 0) + { + SetIsExpandedForChildren(child, isExpanded); + } + } + } } diff --git a/RustTools/Editor/EditorWin.xaml b/RustTools/Editor/EditorWin.xaml index c9e1def..65135f3 100644 --- a/RustTools/Editor/EditorWin.xaml +++ b/RustTools/Editor/EditorWin.xaml @@ -6,6 +6,7 @@ xmlns:controlpages="using:RustTools.Editor" xmlns:controls="using:CommunityToolkit.WinUI.Controls" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" + xmlns:editor="using:RustTools.Editor" xmlns:local="using:RustTools" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" xmlns:windowex="using:WinUIEx" @@ -15,19 +16,20 @@ - + + + AutomationProperties.Name="{x:Bind Name}" + IsExpanded="{x:Bind IsExpanded, Mode=TwoWay}" + ItemsSource="{x:Bind Children}"> - + - + @@ -78,13 +80,15 @@ HorizontalScrollBarVisibility="Auto" VerticalScrollBarVisibility="Auto"> + @@ -107,7 +111,6 @@ Grid.Row="0" Height="auto" IsAddTabButtonVisible="False" - TabCloseRequested="TabView_TabCloseRequested" TabItemsSource="{x:Bind TabViewList}" /> diff --git a/RustTools/Editor/EditorWin.xaml.cs b/RustTools/Editor/EditorWin.xaml.cs index 332b2f7..edb38f5 100644 --- a/RustTools/Editor/EditorWin.xaml.cs +++ b/RustTools/Editor/EditorWin.xaml.cs @@ -1,5 +1,5 @@ using System.Collections.ObjectModel; - +using System.Diagnostics; using Microsoft.UI; using Microsoft.UI.Xaml; using Microsoft.UI.Xaml.Controls; @@ -14,8 +14,14 @@ public sealed partial class EditorWin : WindowEx { private readonly ObservableCollection TabViewList = new(); //Ŀ¼б - public ObservableCollection DataSource = new(); - public EditorWin() + public ObservableCollection DataSource = new(); + + /// + /// ༭ + /// · + /// + /// + public EditorWin(string path) { InitializeComponent(); gj.SetBackTheme(this); @@ -26,16 +32,12 @@ public sealed partial class EditorWin : WindowEx gj.UpdateTitleBar(this, frame.ActualTheme); page.RequestedTheme = frame.ActualTheme; } - //new CodeEditorControl(); - //new Editor. - //WindowManager.Get(this).IsMinimizable = false; - //app = GetAppWindowForCurrentWindow(); - //app.Closing += OnClosing; - //Closed += EditorWin_Closed; - var directoryInfo = new DirectoryInfo("D:\\steam\\steamapps\\common\\Rusted Warfare\\mods\\units\\Ͻ0.90.2"); - DataSource = new EditorLoad().GetData(directoryInfo.FullName); + //Debug.WriteLine(path); + var directoryInfo = new DirectoryInfo(path); Title = directoryInfo.Name; TitleText.Text = directoryInfo.Name; + DataSource = EditorLoad.GetData(directoryInfo.FullName); + treeView.ItemsSource = DataSource; Closed += EditorWin_Closed; } @@ -83,86 +85,7 @@ public sealed partial class EditorWin : WindowEx ClosedDialog = null; } - private Microsoft.UI.Windowing.AppWindow GetAppWindowForCurrentWindow() - { - var hWnd = WindowNative.GetWindowHandle(this); - var myWndId = Win32Interop.GetWindowIdFromWindow(hWnd); - return Microsoft.UI.Windowing.AppWindow.GetFromWindowId(myWndId); - } - - /// - /// ѡ¼ - /// - /// - /// - private void TreeView_ItemInvoked(TreeView sender, TreeViewItemInvokedEventArgs e) - { - - // ȡǰѡе - // ȡ - var invokedItem = e.InvokedItem; - // Ƿظѡ - if (sender.SelectedItem is ExplorerItem selectedItem && invokedItem != null && selectedItem == invokedItem) - { - // ͬһֱӷأнһ - return; - } - if (invokedItem is not ExplorerItem explorerItem) - { - return; - } - if (explorerItem.Type == ExplorerItem.ExplorerItemType.Folder) - { - var directoryInfo = new DirectoryInfo(explorerItem.Dir); - } - } - private void TabView_TabCloseRequested(TabView sender, TabViewTabCloseRequestedEventArgs args) - { - TabViewList.Remove(args.Tab); - } - /// - /// ˫¼ - /// - /// - /// - private void treeView_DoubleTapped(object sender, DoubleTappedRoutedEventArgs e) - { - gj.sc(e.OriginalSource); - var treeViewItem = e.OriginalSource as Grid; - if (treeViewItem == null) { return; } - if (treeViewItem.DataContext is not ExplorerItem explorerItem) { return; } - if (explorerItem.Type == ExplorerItem.ExplorerItemType.File) - { - - // ض TabViewItem - var tabViewItemToFind = TabViewList.FirstOrDefault(item => (item as TabViewItem)?.Tag.ToString() == explorerItem.Dir) as TabViewItem; - - // ȡ TabViewItem λ - if (tabViewItemToFind != null) - { - tabview.SelectedIndex = TabViewList.IndexOf(tabViewItemToFind); - return; - } - var fileInfo = new FileInfo(explorerItem.Dir); - //var name = Path.GetFileNameWithoutExtension(fileInfo.FullName); - var newItem = new TabViewItem() - { - Tag = explorerItem.Dir, - // ȡļչ - Header = fileInfo.Name, - IconSource = new Microsoft.UI.Xaml.Controls.SymbolIconSource() { Symbol = Symbol.Document } - }; - //if(tabview.TabItems.) - var v = wj.dqwb(explorerItem.Dir); - var textControlBox = new RichEditBox(); - //textControlBox.Height = Height; - textControlBox.Document.SetText(Microsoft.UI.Text.TextSetOptions.None, v); - newItem.Content = textControlBox; - TabViewList.Insert(0, newItem); - tabview.SelectedIndex = 0; - } - } } diff --git a/RustTools/Editor/ExplorerItemTemplateSelector.cs b/RustTools/Editor/ExplorerItemTemplateSelector.cs index dd4bfba..7a1b4b2 100644 --- a/RustTools/Editor/ExplorerItemTemplateSelector.cs +++ b/RustTools/Editor/ExplorerItemTemplateSelector.cs @@ -1,74 +1,30 @@ -using System.Collections.ObjectModel; -using System.ComponentModel; + using Microsoft.UI.Xaml; using Microsoft.UI.Xaml.Controls; namespace RustTools.Editor; + public class ExplorerItemTemplateSelector : DataTemplateSelector { - public DataTemplate FolderTemplate + public DataTemplate? FolderTemplate { get; set; } - public DataTemplate FileTemplate + public DataTemplate? FileTemplate { get; set; } protected override DataTemplate SelectTemplateCore(object item) { - var explorerItem = (ExplorerItem)item; - return explorerItem.Type == ExplorerItem.ExplorerItemType.Folder ? FolderTemplate : FileTemplate; - } -} -public class ExplorerItem : INotifyPropertyChanged -{ - public enum ExplorerItemType { Folder, File }; - public event PropertyChangedEventHandler PropertyChanged; - public string? Name - { - get; set; - } - public ExplorerItemType Type - { - get; set; - } - public string? Dir - { - get; set; - } - private ObservableCollection? m_children; - public ObservableCollection Children - { - get + if (((FileItem)item).IsFolder) { - m_children ??= new ObservableCollection(); - return m_children; + return FolderTemplate; } - set => m_children = value; - } - - private bool m_isExpanded; - public bool IsExpanded - { - get => m_isExpanded; - set + else { - if (m_isExpanded != value) - { - m_isExpanded = value; - NotifyPropertyChanged(nameof(IsExpanded)); - } + return FileTemplate; } - } - - private void NotifyPropertyChanged(string propertyName) - { - PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName)); - } - - public static implicit operator ExplorerItem(bool v) - { - throw new NotImplementedException(); + //return base.SelectTemplateCore(item); } } \ No newline at end of file diff --git a/RustTools/Editor/FileItem.cs b/RustTools/Editor/FileItem.cs new file mode 100644 index 0000000..be9a837 --- /dev/null +++ b/RustTools/Editor/FileItem.cs @@ -0,0 +1,99 @@ +using System; +using System.Collections.Generic; +using System.Collections.ObjectModel; +using System.ComponentModel; +using System.Linq; +using System.Runtime.CompilerServices; +using System.Text; +using System.Threading.Tasks; + +namespace RustTools.Editor; +public class FileItem +{ + public string Name + { + get; set; + } + public string Dir + { + get; set; + } + public bool IsFolder + { + get; set; + } + public bool IsExpanded + { + get; set; + } = false; // 用来控制展开状态 + public ObservableCollection Children + { + get; set; + } + + public FileItem() + { + } + public FileItem(bool isFolder) + { + IsFolder = isFolder; + if (isFolder) + { + Children = new ObservableCollection(); + } + } +} + +//public class FileItem : INotifyPropertyChanged +//{ +// private string _name; + +// public string Name +// { +// get => _name; +// set +// { +// _name = value; +// OnPropertyChanged(); +// } +// } + +// public string Dir +// { +// get; set; +// } +// public bool IsFolder +// { +// get; set; +// } +// public ObservableCollection Children +// { +// get; set; +// } + +// public bool IsExpanded +// { +// get; set; +// } = false; // 用来控制展开状态 +// public event PropertyChangedEventHandler PropertyChanged; + +// public FileItem() +// { +// } +// public FileItem(bool isFolder) +// { +// IsFolder = isFolder; +// if (isFolder) +// { +// Children = new ObservableCollection(); +// } +// } + +// protected void OnPropertyChanged([CallerMemberName] string propertyName = null) +// { +// PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName)); +// } + + +//} + diff --git a/RustTools/Views/ModulePage.xaml b/RustTools/Views/ModulePage.xaml index dc89877..1a27fc4 100644 --- a/RustTools/Views/ModulePage.xaml +++ b/RustTools/Views/ModulePage.xaml @@ -53,7 +53,8 @@ diff --git a/RustTools/Views/ModulePage.xaml.cs b/RustTools/Views/ModulePage.xaml.cs index abb61f7..87215a3 100644 --- a/RustTools/Views/ModulePage.xaml.cs +++ b/RustTools/Views/ModulePage.xaml.cs @@ -144,7 +144,7 @@ public sealed partial class ModulePage : Page } - + /// /// 解压模组 /// @@ -255,7 +255,7 @@ public sealed partial class ModulePage : Page /// /// /// - private void BasicGridView_DoubleTapped(object sender, Microsoft.UI.Xaml.Input.DoubleTappedRoutedEventArgs e) + private void BasicGridView_DoubleTapped(object sender, Microsoft.UI.Xaml.Input.DoubleTappedRoutedEventArgs e) { var gridView = sender as GridView; @@ -269,7 +269,8 @@ public sealed partial class ModulePage : Page { // 在这里处理双击项 var IsRwmod = clickedItem.IsRwmod; // 假设你的项有一个 Name 属性 - if (IsRwmod) { + if (IsRwmod) + { UnzipRwmod(clickedItem); } @@ -300,8 +301,8 @@ public sealed partial class ModulePage : Page { XamlRoot = XamlRoot }; - var h= ((Panel) Content).ActualHeight; - postRwmod.Height =h-50; + var h = ((Panel)Content).ActualHeight; + postRwmod.Height = h - 50; contentDialog.Content = postRwmod; // 订阅 Closing 事件 contentDialog.Closing += Dialog.DialogNotEsc; @@ -319,7 +320,29 @@ public sealed partial class ModulePage : Page /// private void Button_OpenDir(object sender, RoutedEventArgs e) { - wj.OpenFileExplorer(ViewModel.ListMod[0].Dri); + var view = sender as MenuFlyoutItem; + // 替换为实际的数据类型 + if (view?.DataContext is DataObject clickedItem) + { + wj.OpenFileExplorer(clickedItem.Dri); + } + } + /// + /// 打开模组_文件夹 + /// + /// + /// + private void Button_OpenMod(object sender, RoutedEventArgs e) + { + var view = sender as MenuFlyoutItem; + // 替换为实际的数据类型 + if (view?.DataContext is DataObject clickedItem) + { + if (!clickedItem.IsRwmod) + { + new Editor.EditorWin(clickedItem.Dri).Show(); + } + } } } public class MyItemTemplateSelector : DataTemplateSelector