add icon for pathing ui

This commit is contained in:
辉鸭蛋 2024-10-24 00:48:58 +08:00
parent b3f6002846
commit 404e7215fa
7 changed files with 119 additions and 8 deletions

View File

@ -70,7 +70,7 @@
<PackageReference Include="Vanara.PInvoke.User32" Version="4.0.2" /> <PackageReference Include="Vanara.PInvoke.User32" Version="4.0.2" />
<PackageReference Include="WPF-UI" Version="3.0.5" /> <PackageReference Include="WPF-UI" Version="3.0.5" />
<PackageReference Include="WPF-UI.Tray" Version="3.0.5" /> <PackageReference Include="WPF-UI.Tray" Version="3.0.5" />
<PackageReference Include="WPF-UI.Violeta" Version="3.0.5.18" /> <PackageReference Include="WPF-UI.Violeta" Version="3.0.5.20" />
<PackageReference Include="YoloV8" Version="4.1.7" /> <PackageReference Include="YoloV8" Version="4.1.7" />
<PackageReference Include="gong-wpf-dragdrop" Version="3.2.1" /> <PackageReference Include="gong-wpf-dragdrop" Version="3.2.1" />
</ItemGroup> </ItemGroup>

View File

@ -1,6 +1,7 @@
using BetterGenshinImpact.Core.Config; using BetterGenshinImpact.Core.Config;
using BetterGenshinImpact.Core.Script.WebView; using BetterGenshinImpact.Core.Script.WebView;
using BetterGenshinImpact.GameTask; using BetterGenshinImpact.GameTask;
using BetterGenshinImpact.Helpers;
using BetterGenshinImpact.Helpers.Http; using BetterGenshinImpact.Helpers.Http;
using BetterGenshinImpact.Model; using BetterGenshinImpact.Model;
using BetterGenshinImpact.View.Controls.Webview; using BetterGenshinImpact.View.Controls.Webview;
@ -16,6 +17,7 @@ using System.Linq;
using System.Net.Http; using System.Net.Http;
using System.Threading.Tasks; using System.Threading.Tasks;
using System.Windows; using System.Windows;
using Vanara.PInvoke;
using Wpf.Ui.Violeta.Controls; using Wpf.Ui.Violeta.Controls;
namespace BetterGenshinImpact.Core.Script; namespace BetterGenshinImpact.Core.Script;
@ -95,7 +97,20 @@ public class ScriptRepoUpdater : Singleton<ScriptRepoUpdater>
var updated = false; var updated = false;
// 检查仓库是否存在,不存在则下载 // 检查仓库是否存在,不存在则下载
if (!Directory.Exists(CenterRepoPath)) var needDownload = false;
if (Directory.Exists(CenterRepoPath))
{
var p = Directory.GetFiles(CenterRepoPath, "repo.json", SearchOption.AllDirectories).FirstOrDefault();
if (p is null)
{
needDownload = true;
}
}
else
{
needDownload = true;
}
if (needDownload)
{ {
await DownloadRepoAndUnzip(string.Format(fastProxyUrl, url)); await DownloadRepoAndUnzip(string.Format(fastProxyUrl, url));
updated = true; updated = true;
@ -190,7 +205,7 @@ public class ScriptRepoUpdater : Singleton<ScriptRepoUpdater>
// 删除旧文件夹 // 删除旧文件夹
if (Directory.Exists(CenterRepoPath)) if (Directory.Exists(CenterRepoPath))
{ {
Directory.Delete(CenterRepoPath, true); DirectoryHelper.DeleteReadOnlyDirectory(CenterRepoPath);
} }
// 使用 System.IO.Compression 解压 // 使用 System.IO.Compression 解压
@ -349,6 +364,9 @@ public class ScriptRepoUpdater : Singleton<ScriptRepoUpdater>
} }
CopyDirectory(scriptPath, destPath); CopyDirectory(scriptPath, destPath);
// 图标处理
DealWithIconFolder(destPath);
} }
else if (File.Exists(scriptPath)) else if (File.Exists(scriptPath))
{ {
@ -425,4 +443,25 @@ public class ScriptRepoUpdater : Singleton<ScriptRepoUpdater>
_webWindow.Activate(); _webWindow.Activate();
} }
} }
/// <summary>
/// 处理带有 icon.ico 和 desktop.ini 的文件夹
/// </summary>
/// <param name="folderPath"></param>
private void DealWithIconFolder(string folderPath)
{
if (Directory.Exists(folderPath)
&& File.Exists(Path.Combine(folderPath, "desktop.ini")))
{
// 使用 Vanara 库中的 SetFileAttributes 函数设置文件夹属性
if (Kernel32.SetFileAttributes(folderPath, FileFlagsAndAttributes.FILE_ATTRIBUTE_READONLY))
{
Debug.WriteLine($"成功将文件夹设置为只读: {folderPath}");
}
else
{
Debug.WriteLine($"无法设置文件夹为只读: {folderPath}");
}
}
}
} }

View File

@ -0,0 +1,45 @@
using System.IO;
namespace BetterGenshinImpact.Helpers;
public class DirectoryHelper
{
public static void DeleteReadOnlyDirectory(string directoryPath)
{
if (Directory.Exists(directoryPath))
{
// 获取目录信息
var directoryInfo = new DirectoryInfo(directoryPath);
// 移除目录及其内容的只读属性
RemoveReadOnlyAttribute(directoryInfo);
// 删除目录
Directory.Delete(directoryPath, true);
}
}
private static void RemoveReadOnlyAttribute(DirectoryInfo directoryInfo)
{
// 移除目录的只读属性
if (directoryInfo.Attributes.HasFlag(FileAttributes.ReadOnly))
{
directoryInfo.Attributes &= ~FileAttributes.ReadOnly;
}
// 移除文件的只读属性
foreach (var file in directoryInfo.GetFiles())
{
if (file.Attributes.HasFlag(FileAttributes.ReadOnly))
{
file.Attributes &= ~FileAttributes.ReadOnly;
}
}
// 递归处理子目录
foreach (var subDirectory in directoryInfo.GetDirectories())
{
RemoveReadOnlyAttribute(subDirectory);
}
}
}

View File

@ -1,10 +1,13 @@
using BetterGenshinImpact.Model; using BetterGenshinImpact.Model;
using System.IO; using System.IO;
using System.Linq;
namespace BetterGenshinImpact.Helpers.Ui; namespace BetterGenshinImpact.Helpers.Ui;
public class FileTreeNodeHelper public class FileTreeNodeHelper
{ {
public static string[] AllowedExtensions { get; set; } = [".json"];
public static FileTreeNode<T> LoadDirectory<T>(string directoryPath) public static FileTreeNode<T> LoadDirectory<T>(string directoryPath)
{ {
if (!Directory.Exists(directoryPath)) if (!Directory.Exists(directoryPath))
@ -39,7 +42,7 @@ public class FileTreeNodeHelper
LoadSubDirectories(directory, directoryNode); LoadSubDirectories(directory, directoryNode);
} }
foreach (var file in directoryInfo.GetFiles()) foreach (var file in directoryInfo.GetFiles().Where(f => AllowedExtensions.Contains(f.Extension)))
{ {
var fileNode = new FileTreeNode<T> var fileNode = new FileTreeNode<T>
{ {

View File

@ -36,6 +36,12 @@ public partial class FileTreeNode<T> : ObservableObject
[ObservableProperty] [ObservableProperty]
private string? _filePath; private string? _filePath;
/// <summary>
/// 展示图标路径
/// </summary>
[ObservableProperty]
private string? _iconFilePath;
// 节点的值 // 节点的值
[ObservableProperty] [ObservableProperty]
private T? _value; private T? _value;

View File

@ -8,6 +8,7 @@
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:pages="clr-namespace:BetterGenshinImpact.ViewModel.Pages" xmlns:pages="clr-namespace:BetterGenshinImpact.ViewModel.Pages"
xmlns:ui="http://schemas.lepo.co/wpfui/2022/xaml" xmlns:ui="http://schemas.lepo.co/wpfui/2022/xaml"
xmlns:vio="http://schemas.lepo.co/wpfui/2022/xaml/violeta"
d:DataContext="{d:DesignInstance Type=pages:MapPathingViewModel}" d:DataContext="{d:DesignInstance Type=pages:MapPathingViewModel}"
d:DesignHeight="600" d:DesignHeight="600"
d:DesignWidth="800" d:DesignWidth="800"
@ -90,13 +91,19 @@
<ui:GridViewColumn Width="{Binding ActualWidth, ElementName=TreeColumnStar}" Header="名称"> <ui:GridViewColumn Width="{Binding ActualWidth, ElementName=TreeColumnStar}" Header="名称">
<ui:GridViewColumn.CellTemplate> <ui:GridViewColumn.CellTemplate>
<DataTemplate> <DataTemplate>
<ui:TreeRowExpander Content="{Binding FileName}" /> <ui:TreeRowExpander>
<ui:TreeRowExpander.Content>
<ui:StackPanel Margin="8,0,0,0"
Orientation="Horizontal"
Spacing="8">
<Image Height="16" Source="{Binding IconFilePath, Converter={x:Static vio:PathToIconConverter.Instance}}" />
<TextBlock VerticalAlignment="Center" Text="{Binding FileName}" />
</ui:StackPanel>
</ui:TreeRowExpander.Content>
</ui:TreeRowExpander>
</DataTemplate> </DataTemplate>
</ui:GridViewColumn.CellTemplate> </ui:GridViewColumn.CellTemplate>
</ui:GridViewColumn> </ui:GridViewColumn>
<!--<ui:GridViewColumn Width="120"
DisplayMemberBinding="{Binding Author}"
Header="作者" />-->
</GridViewColumnCollection> </GridViewColumnCollection>
</ui:TreeListView.Columns> </ui:TreeListView.Columns>
<ui:TreeListView.ItemTemplate> <ui:TreeListView.ItemTemplate>

View File

@ -49,6 +49,16 @@ public partial class MapPathingViewModel : ObservableObject, INavigationAware, I
// 循环写入 root.Children // 循环写入 root.Children
foreach (var item in root.Children) foreach (var item in root.Children)
{ {
// 补充图标
if (!string.IsNullOrEmpty(item.FilePath) && File.Exists(Path.Combine(item.FilePath, "icon.ico")))
{
item.IconFilePath = Path.Combine(item.FilePath, "icon.ico");
}
else
{
item.IconFilePath = item.FilePath;
}
TreeList.Add(item); TreeList.Add(item);
} }
} }
@ -91,6 +101,7 @@ public partial class MapPathingViewModel : ObservableObject, INavigationAware, I
{ {
return; return;
} }
if (item.IsDirectory) if (item.IsDirectory)
{ {
Toast.Warning("执行多个地图追踪任务的时候,请使用调度器功能"); Toast.Warning("执行多个地图追踪任务的时候,请使用调度器功能");