From a748da19095df55e2e15aa54c0cad3fc34c69e78 Mon Sep 17 00:00:00 2001
From: sin365 <353374337@qq.com>
Date: Wed, 10 Sep 2025 20:25:29 +0800
Subject: [PATCH] =?UTF-8?q?=E5=AE=8C=E5=96=84NS=20IO=E7=9A=84API?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
.../Assets/Plugins/AxiNSApi/AxiNSIO.cs | 1332 ++++++++++-------
1 file changed, 787 insertions(+), 545 deletions(-)
diff --git a/AxibugEmuOnline.Client/Assets/Plugins/AxiNSApi/AxiNSIO.cs b/AxibugEmuOnline.Client/Assets/Plugins/AxiNSApi/AxiNSIO.cs
index 9ad3c4a9..a9211848 100644
--- a/AxibugEmuOnline.Client/Assets/Plugins/AxiNSApi/AxiNSIO.cs
+++ b/AxibugEmuOnline.Client/Assets/Plugins/AxiNSApi/AxiNSIO.cs
@@ -1,26 +1,27 @@
#if UNITY_SWITCH
using nn.fs;
+using System.Text.RegularExpressions;
#endif
using System.Collections.Generic;
-using System.Text.RegularExpressions;
+using System;
public class AxiNSIO
{
- string save_name => AxiNS.instance.mount.SaveMountName;
- public string save_path => $"{save_name}:/";
+ string save_name => AxiNS.instance.mount.SaveMountName;
+ public string save_path => $"{save_name}:/";
#if UNITY_SWITCH
- private FileHandle fileHandle = new nn.fs.FileHandle();
+ private FileHandle fileHandle = new nn.fs.FileHandle();
#endif
- static object commitLock = new object();
+ static object commitLock = new object();
- static bool bDirty = false;
+ static bool bDirty = false;
- bool CommitSave()
- {
- lock (commitLock)
- {
+ bool CommitSave()
+ {
+ lock (commitLock)
+ {
#if UNITY_SWITCH && !UNITY_EDITOR
// 阻止用户在保存时,退出游戏 Switch 条例 0080
@@ -39,242 +40,265 @@ public class AxiNSIO
bDirty = false;
return true;
#else
- return false;
+ return false;
#endif
- }
+ }
- }
+ }
- void SetCommitDirty()
- {
- lock (commitLock)
- {
- bDirty = true;
- }
- }
+ void SetCommitDirty()
+ {
+ lock (commitLock)
+ {
+ bDirty = true;
+ }
+ }
- public void ApplyAutoCommit()
- {
- bool temp;
- lock (commitLock)
- {
- temp = bDirty;
- }
+ public void ApplyAutoCommit()
+ {
+ bool temp;
+ lock (commitLock)
+ {
+ temp = bDirty;
+ }
- if (temp)
- {
- CommitSave();
- }
- }
+ if (temp)
+ {
+ CommitSave();
+ }
+ }
- ///
- /// 检查Path是否存在
- ///
- ///
- ///
- public bool CheckPathExists(string filePath)
- {
+ ///
+ /// 检查Path是否存在
+ ///
+ ///
+ ///
+ public bool CheckPathExists(string filePath)
+ {
#if !UNITY_SWITCH
return false;
#else
- nn.fs.EntryType entryType = 0;
- nn.Result result = nn.fs.FileSystem.GetEntryType(ref entryType, filePath);
- //result.abortUnlessSuccess();
- //这个异常捕获。真的别扭
+ nn.fs.EntryType entryType = 0;
+ nn.Result result = nn.fs.FileSystem.GetEntryType(ref entryType, filePath);
+ //result.abortUnlessSuccess();
+ //这个异常捕获。真的别扭
- //日,FileSystem.ResultPathAlreadyExists 貌似不太行
- //return nn.fs.FileSystem.ResultPathAlreadyExists.Includes(result);
- return !nn.fs.FileSystem.ResultPathNotFound.Includes(result);
+ //日,FileSystem.ResultPathAlreadyExists 貌似不太行
+ //return nn.fs.FileSystem.ResultPathAlreadyExists.Includes(result);
+ return !nn.fs.FileSystem.ResultPathNotFound.Includes(result);
#endif
- }
- ///
- /// 检查Path是否不存在
- ///
- ///
- ///
- public bool CheckPathNotFound(string filePath)
- {
+ }
+ ///
+ /// 检查Path是否不存在
+ ///
+ ///
+ ///
+ public bool CheckPathNotFound(string filePath)
+ {
#if !UNITY_SWITCH
return false;
#else
- nn.fs.EntryType entryType = 0;
- nn.Result result = nn.fs.FileSystem.GetEntryType(ref entryType, filePath);
- //这个异常捕获。真的别扭
- return nn.fs.FileSystem.ResultPathNotFound.Includes(result);
+ nn.fs.EntryType entryType = 0;
+ nn.Result result = nn.fs.FileSystem.GetEntryType(ref entryType, filePath);
+ //这个异常捕获。真的别扭
+ return nn.fs.FileSystem.ResultPathNotFound.Includes(result);
#endif
- }
- ///
- /// 创建目录,目录存在也会返回true
- ///
- ///
- ///
- public bool CreateDir(string filePath)
- {
- lock (commitLock)
- {
+ }
+ ///
+ /// 创建目录,目录存在也会返回true
+ ///
+ ///
+ ///
+ public bool CreateDir(string dirpath)
+ {
+ UnityEngine.Debug.Log($"CreateDir: {dirpath}");
+ lock (commitLock)
+ {
#if !UNITY_SWITCH
return false;
#else
- // 使用封装函数检查和创建父目录
- if (!EnsureParentDirectory(filePath, true))
- {
- UnityEngine.Debug.LogError($"无法确保父目录,文件写入取消: {filePath}");
- return false;
- }
- return true;
+ // 使用封装函数检查和创建父目录
+ if (!EnsureParentDirectory(dirpath, true))
+ {
+ UnityEngine.Debug.LogError($"无法确保父目录,文件写入取消: {dirpath}");
+ return false;
+ }
+ return true;
#endif
- }
- }
+ }
+ }
- ///
- /// 保存并创建文件(如果目录不存在回先自动创建目录)
- ///
- ///
- ///
- ///
- public bool FileToSaveWithCreate(string filePath, System.IO.MemoryStream ms)
- {
- return FileToSaveWithCreate(filePath, ms.ToArray());
- }
- ///
- /// 保存并创建文件(如果目录不存在回先自动创建目录)
- ///
- ///
- ///
- ///
- public AxiNSWait_FileToSaveByMSWithCreate FileToSaveWithCreateAsync(string filePath, System.IO.MemoryStream ms)
- {
- var wait = new AxiNSWait_FileToSaveByMSWithCreate(filePath, ms);
- AxiNS.instance.wait.AddWait(wait);
- return wait;
- }
+ ///
+ /// 保存并创建文件(如果目录不存在回先自动创建目录)
+ ///
+ ///
+ ///
+ ///
+ public bool FileToSaveWithCreate(string filePath, System.IO.MemoryStream ms)
+ {
+ return FileToSaveWithCreate(filePath, ms.ToArray());
+ }
+ ///
+ /// 保存并创建文件(如果目录不存在回先自动创建目录)
+ ///
+ ///
+ ///
+ ///
+ public AxiNSWait_FileToSaveByMSWithCreate FileToSaveWithCreateAsync(string filePath, System.IO.MemoryStream ms)
+ {
+ var wait = new AxiNSWait_FileToSaveByMSWithCreate(filePath, ms);
+ AxiNS.instance.wait.AddWait(wait);
+ return wait;
+ }
- ///
- /// 保存并创建文件(如果目录不存在回先自动创建目录)
- ///
- ///
- ///
- /// 是否立即Commit到物理存储
- ///
- public bool FileToSaveWithCreate(string filePath, byte[] data, bool immediatelyCommit = true)
- {
- lock (commitLock)
- {
+ ///
+ /// 保存并创建文件(如果目录不存在回先自动创建目录)
+ ///
+ ///
+ ///
+ /// 是否立即Commit到物理存储
+ ///
+ public bool FileToSaveWithCreate(string filePath, byte[] data, bool immediatelyCommit = true)
+ {
+ UnityEngine.Debug.Log($"FileToSaveWithCreate: {filePath}");
+ lock (commitLock)
+ {
#if !UNITY_SWITCH
return false;
#else
- if (!AxiNS.instance.mount.SaveIsMount)
- {
- UnityEngine.Debug.LogError($"Save 尚未挂载,无法存储 {filePath}");
- return false;
- }
+ if (!AxiNS.instance.mount.SaveIsMount)
+ {
+ UnityEngine.Debug.LogError($"Save 尚未挂载,无法存储 {filePath}");
+ return false;
+ }
+
+ nn.Result result;
+
+ //取出父级目录
+ string dirpath = string.Empty;
+ //string filePath = "save:/AxibugEmu/Caches/Texture/516322966";
+ string mountRoot = null;
+ int colonSlashIndex = filePath.IndexOf(":/");
+ if (colonSlashIndex > 0)
+ mountRoot = filePath.Substring(0, colonSlashIndex + 1); // 例如 "save:"
+
+ int lastSlashIndex = filePath.LastIndexOf('/');
+ if (lastSlashIndex >= 0)
+ {
+ string parent = filePath.Substring(0, lastSlashIndex);
+ if (mountRoot != null && !parent.Equals(mountRoot, StringComparison.OrdinalIgnoreCase))
+ dirpath = parent;
+ }
+
+
+ if (!string.IsNullOrWhiteSpace(dirpath))
+ {
+ // 使用封装函数检查和创建父目录
+ if (!EnsureParentDirectory(dirpath, true))
+ {
+ UnityEngine.Debug.LogError($"无法确保父目录,文件写入取消: {filePath}");
+ return false;
+ }
+ }
+
+ //string directoryPath = System.IO.Path.GetDirectoryName(filePath.Replace(save_path, ""));
+ //string fullDirectoryPath = $"{save_path}{directoryPath}";
+ //UnityEngine.Debug.Log($"检查父目录: {fullDirectoryPath}");
+
+ //nn.fs.EntryType entryType = 0;
+ //result = nn.fs.FileSystem.GetEntryType(ref entryType, fullDirectoryPath);
+ //if (!result.IsSuccess() && nn.fs.FileSystem.ResultPathNotFound.Includes(result))
+ //{
+ // UnityEngine.Debug.Log($"父目录 {fullDirectoryPath} 不存在,尝试创建 (判断依据 result=>{result.ToString()})");
+ // result = nn.fs.Directory.Create(fullDirectoryPath);
+ // if (!result.IsSuccess())
+ // {
+ // UnityEngine.Debug.LogError($"创建父目录失败: {result.GetErrorInfo()}");
+ // return false;
+ // }
+ // UnityEngine.Debug.Log($"父目录 {fullDirectoryPath} 创建成功");
+ //}
+ //else if (result.IsSuccess() && entryType != nn.fs.EntryType.Directory)
+ //{
+ // UnityEngine.Debug.LogError($"路径 {fullDirectoryPath} 已存在,但不是目录");
+ // return false;
+ //}
+ //else if (!result.IsSuccess())
+ //{
+ // UnityEngine.Debug.LogError($"检查父目录失败: {result.GetErrorInfo()}");
+ // return false;
+ //}
- nn.Result result;
#if UNITY_SWITCH && !UNITY_EDITOR
// 阻止用户在保存时,退出游戏
// Switch 条例 0080
UnityEngine.Switch.Notification.EnterExitRequestHandlingSection();
#endif
- // 使用封装函数检查和创建父目录
- if (!EnsureParentDirectory(filePath, true))
- {
- UnityEngine.Debug.LogError($"无法确保父目录,文件写入取消: {filePath}");
- return false;
- }
+ if (CheckPathNotFound(filePath))
+ {
+ UnityEngine.Debug.Log($"文件({filePath})不存在需要创建");
+ result = nn.fs.File.Create(filePath, data.Length); //this makes a file the size of your save journal. You may want to make a file smaller than this.
+ //result.abortUnlessSuccess();
+ if (!result.IsSuccess())
+ {
+ UnityEngine.Debug.LogError($"创建文件失败 {filePath} : " + result.GetErrorInfo());
+ return false;
+ }
+ //读取文件Handle
+ result = File.Open(ref fileHandle, filePath, OpenFileMode.Write);
+ }
+ else
+ {
+ //读取文件Handle
+ result = File.Open(ref fileHandle, filePath, OpenFileMode.Write);
+ long currsize = 0;
+ File.GetSize(ref currsize, fileHandle);
+ if (currsize == data.Length)
+ {
+ UnityEngine.Debug.Log($"文件({filePath})存在,长度一致,不用重新创建");
+ }
+ else
+ {
+ UnityEngine.Debug.Log($"文件({filePath})存在,长度不一致,先删除再重建");
+ nn.fs.File.Close(fileHandle);
+ //删除
+ File.Delete(filePath);
+ //重新创建
+ result = nn.fs.File.Create(filePath, data.Length);
+ if (!result.IsSuccess())
+ {
+ UnityEngine.Debug.LogError($"创建文件失败 {filePath} : " + result.GetErrorInfo());
+ return false;
+ }
+ //重新读取文件Handle
+ result = File.Open(ref fileHandle, filePath, OpenFileMode.Write);
+ }
+ }
- //string directoryPath = System.IO.Path.GetDirectoryName(filePath.Replace(save_path, ""));
- //string fullDirectoryPath = $"{save_path}{directoryPath}";
- //UnityEngine.Debug.Log($"检查父目录: {fullDirectoryPath}");
+ // //OpenFileMode.AllowAppend 好像不可用
+ // //result = File.Open(ref fileHandle, filePath, OpenFileMode.AllowAppend);
+ // result = File.Open(ref fileHandle, filePath, OpenFileMode.Write);
- //nn.fs.EntryType entryType = 0;
- //result = nn.fs.FileSystem.GetEntryType(ref entryType, fullDirectoryPath);
- //if (!result.IsSuccess() && nn.fs.FileSystem.ResultPathNotFound.Includes(result))
- //{
- // UnityEngine.Debug.Log($"父目录 {fullDirectoryPath} 不存在,尝试创建 (判断依据 result=>{result.ToString()})");
- // result = nn.fs.Directory.Create(fullDirectoryPath);
- // if (!result.IsSuccess())
- // {
- // UnityEngine.Debug.LogError($"创建父目录失败: {result.GetErrorInfo()}");
- // return false;
- // }
- // UnityEngine.Debug.Log($"父目录 {fullDirectoryPath} 创建成功");
- //}
- //else if (result.IsSuccess() && entryType != nn.fs.EntryType.Directory)
- //{
- // UnityEngine.Debug.LogError($"路径 {fullDirectoryPath} 已存在,但不是目录");
- // return false;
- //}
- //else if (!result.IsSuccess())
- //{
- // UnityEngine.Debug.LogError($"检查父目录失败: {result.GetErrorInfo()}");
- // return false;
- //}
+ //result.abortUnlessSuccess();
+ if (!result.IsSuccess())
+ {
+ UnityEngine.Debug.LogError($"失败 File.Open(ref filehandle, {filePath}, OpenFileMode.Write): " + result.GetErrorInfo());
+ return false;
+ }
+ UnityEngine.Debug.Log($"成功 File.Open(ref filehandle, {filePath}, OpenFileMode.Write)");
- if (CheckPathNotFound(filePath))
- {
- UnityEngine.Debug.Log($"文件({filePath})不存在需要创建");
- result = nn.fs.File.Create(filePath, data.Length); //this makes a file the size of your save journal. You may want to make a file smaller than this.
- //result.abortUnlessSuccess();
- if (!result.IsSuccess())
- {
- UnityEngine.Debug.LogError($"创建文件失败 {filePath} : " + result.GetErrorInfo());
- return false;
- }
- //读取文件Handle
- result = File.Open(ref fileHandle, filePath, OpenFileMode.Write);
- }
- else
- {
- //读取文件Handle
- result = File.Open(ref fileHandle, filePath, OpenFileMode.Write);
- long currsize = 0;
- File.GetSize(ref currsize, fileHandle);
- if (currsize == data.Length)
- {
- UnityEngine.Debug.Log($"文件({filePath})存在,长度一致,不用重新创建");
- }
- else
- {
- UnityEngine.Debug.Log($"文件({filePath})存在,长度不一致,先删除再重建");
- nn.fs.File.Close(fileHandle);
- //删除
- File.Delete(filePath);
- //重新创建
- result = nn.fs.File.Create(filePath, data.Length);
- if (!result.IsSuccess())
- {
- UnityEngine.Debug.LogError($"创建文件失败 {filePath} : " + result.GetErrorInfo());
- return false;
- }
- //重新读取文件Handle
- result = File.Open(ref fileHandle, filePath, OpenFileMode.Write);
- }
- }
+ //nn.fs.WriteOption.Flush 应该就是覆盖写入
+ result = nn.fs.File.Write(fileHandle, 0, data, data.Length, nn.fs.WriteOption.Flush); // Writes and flushes the write at the same time
+ //result.abortUnlessSuccess();
+ if (!result.IsSuccess())
+ {
+ UnityEngine.Debug.LogError("写入文件失败: " + result.GetErrorInfo());
+ return false;
+ }
+ UnityEngine.Debug.Log("写入文件成功: " + filePath);
- // //OpenFileMode.AllowAppend 好像不可用
- // //result = File.Open(ref fileHandle, filePath, OpenFileMode.AllowAppend);
- // result = File.Open(ref fileHandle, filePath, OpenFileMode.Write);
-
- //result.abortUnlessSuccess();
- if (!result.IsSuccess())
- {
- UnityEngine.Debug.LogError($"失败 File.Open(ref filehandle, {filePath}, OpenFileMode.Write): " + result.GetErrorInfo());
- return false;
- }
- UnityEngine.Debug.Log($"成功 File.Open(ref filehandle, {filePath}, OpenFileMode.Write)");
-
- //nn.fs.WriteOption.Flush 应该就是覆盖写入
- result = nn.fs.File.Write(fileHandle, 0, data, data.Length, nn.fs.WriteOption.Flush); // Writes and flushes the write at the same time
- //result.abortUnlessSuccess();
- if (!result.IsSuccess())
- {
- UnityEngine.Debug.LogError("写入文件失败: " + result.GetErrorInfo());
- return false;
- }
- UnityEngine.Debug.Log("写入文件成功: " + filePath);
-
- nn.fs.File.Close(fileHandle);
+ nn.fs.File.Close(fileHandle);
#if UNITY_SWITCH && !UNITY_EDITOR
@@ -282,56 +306,56 @@ public class AxiNSIO
UnityEngine.Switch.Notification.LeaveExitRequestHandlingSection();
#endif
- if (immediatelyCommit)
- {
- //必须得提交,否则没有真实写入
- return CommitSave();
- }
- else
- {
- SetCommitDirty();
- return true;
- }
+ if (immediatelyCommit)
+ {
+ //必须得提交,否则没有真实写入
+ return CommitSave();
+ }
+ else
+ {
+ SetCommitDirty();
+ return true;
+ }
#endif
- }
- }
- ///
- /// 保存并创建文件(如果目录不存在回先自动创建目录)
- ///
- ///
- ///
- ///
- public AxiNSWait_FileToSaveWithCreate FileToSaveWithCreateAsync(string filePath, byte[] data)
- {
- var wait = new AxiNSWait_FileToSaveWithCreate(filePath, data);
- AxiNS.instance.wait.AddWait(wait);
- return wait;
- }
- public byte[] LoadSwitchDataFile(string filename)
- {
- byte[] outputData;
- LoadSwitchDataFile(filename, out outputData);
- return outputData;
- }
+ }
+ }
+ ///
+ /// 保存并创建文件(如果目录不存在回先自动创建目录)
+ ///
+ ///
+ ///
+ ///
+ public AxiNSWait_FileToSaveWithCreate FileToSaveWithCreateAsync(string filePath, byte[] data)
+ {
+ var wait = new AxiNSWait_FileToSaveWithCreate(filePath, data);
+ AxiNS.instance.wait.AddWait(wait);
+ return wait;
+ }
+ public byte[] LoadSwitchDataFile(string filename)
+ {
+ byte[] outputData;
+ LoadSwitchDataFile(filename, out outputData);
+ return outputData;
+ }
- public bool LoadSwitchDataFile(string filename, ref System.IO.MemoryStream ms)
- {
- byte[] outputData;
- if (LoadSwitchDataFile(filename, out outputData))
- {
- using (System.IO.BinaryWriter writer = new System.IO.BinaryWriter(ms))
- {
- writer.Write(outputData);
- }
- return true;
- }
- return false;
- }
- public bool LoadSwitchDataFile(string filename, out byte[] outputData)
- {
+ public bool LoadSwitchDataFile(string filename, ref System.IO.MemoryStream ms)
+ {
+ byte[] outputData;
+ if (LoadSwitchDataFile(filename, out outputData))
+ {
+ using (System.IO.BinaryWriter writer = new System.IO.BinaryWriter(ms))
+ {
+ writer.Write(outputData);
+ }
+ return true;
+ }
+ return false;
+ }
+ public bool LoadSwitchDataFile(string filename, out byte[] outputData)
+ {
#if !UNITY_SWITCH || UNITY_EDITOR
- outputData = null;
- return false;
+ outputData = null;
+ return false;
#else
outputData = null;
if (!AxiNS.instance.mount.SaveIsMount)
@@ -379,104 +403,104 @@ public class AxiNSIO
outputData = loadedData;
return true;
#endif
- }
- public AxiNSWait_LoadSwitchDataFile LoadSwitchDataFileAsync(string filename)
- {
- var wait = new AxiNSWait_LoadSwitchDataFile(filename);
- AxiNS.instance.wait.AddWait(wait);
- return wait;
- }
+ }
+ public AxiNSWait_LoadSwitchDataFile LoadSwitchDataFileAsync(string filename)
+ {
+ var wait = new AxiNSWait_LoadSwitchDataFile(filename);
+ AxiNS.instance.wait.AddWait(wait);
+ return wait;
+ }
- public bool GetDirectoryFiles(string path, out string[] entrys)
- {
+ public bool GetDirectoryFiles(string path, out string[] entrys)
+ {
#if !UNITY_SWITCH || UNITY_EDITOR
- entrys = null;
- return false;
+ entrys = null;
+ return false;
#else
return GetDirectoryEntrys(path,nn.fs.OpenDirectoryMode.File,out entrys);
#endif
- }
+ }
- public bool GetDirectoryDirs(string path, out string[] entrys)
- {
+ public bool GetDirectoryDirs(string path, out string[] entrys)
+ {
#if !UNITY_SWITCH || UNITY_EDITOR
- entrys = null;
- return false;
+ entrys = null;
+ return false;
#else
return GetDirectoryEntrys(path, nn.fs.OpenDirectoryMode.Directory, out entrys);
#endif
- }
+ }
#if UNITY_SWITCH
- public bool GetDirectoryEntrys(string path, nn.fs.OpenDirectoryMode type, out string[] entrys)
- {
- nn.fs.DirectoryHandle eHandle = new nn.fs.DirectoryHandle();
- nn.Result result = nn.fs.Directory.Open(ref eHandle, path, type);
- if (nn.fs.FileSystem.ResultPathNotFound.Includes(result))
- {
- UnityEngine.Debug.Log($"目录 {path} 不存在");
- entrys = null;
- return false;
- }
- long entryCount = 0;
- nn.fs.Directory.GetEntryCount(ref entryCount, eHandle);
- nn.fs.DirectoryEntry[] entries = new nn.fs.DirectoryEntry[entryCount];
- long actualEntries = 0;
- nn.fs.Directory.Read(ref actualEntries, entries, eHandle, entryCount);
+ public bool GetDirectoryEntrys(string path, nn.fs.OpenDirectoryMode type, out string[] entrys)
+ {
+ nn.fs.DirectoryHandle eHandle = new nn.fs.DirectoryHandle();
+ nn.Result result = nn.fs.Directory.Open(ref eHandle, path, type);
+ if (nn.fs.FileSystem.ResultPathNotFound.Includes(result))
+ {
+ UnityEngine.Debug.Log($"目录 {path} 不存在");
+ entrys = null;
+ return false;
+ }
+ long entryCount = 0;
+ nn.fs.Directory.GetEntryCount(ref entryCount, eHandle);
+ nn.fs.DirectoryEntry[] entries = new nn.fs.DirectoryEntry[entryCount];
+ long actualEntries = 0;
+ nn.fs.Directory.Read(ref actualEntries, entries, eHandle, entryCount);
- entrys = new string[actualEntries];
- for (int i = 0; i < actualEntries; i++)
- {
- entrys[i] = System.IO.Path.Combine(path, entries[i].name);
- }
- nn.fs.Directory.Close(eHandle);
- return true;
- }
+ entrys = new string[actualEntries];
+ for (int i = 0; i < actualEntries; i++)
+ {
+ entrys[i] = System.IO.Path.Combine(path, entries[i].name);
+ }
+ nn.fs.Directory.Close(eHandle);
+ return true;
+ }
#endif
- public bool GetDirectoryEntrysFullRecursion(string path, out string[] entrys)
- {
+ public bool GetDirectoryEntrysFullRecursion(string path, out string[] entrys)
+ {
#if UNITY_SWITCH
- nn.fs.DirectoryHandle eHandle = new nn.fs.DirectoryHandle();
- nn.Result result = nn.fs.Directory.Open(ref eHandle, path, OpenDirectoryMode.All);
- if (nn.fs.FileSystem.ResultPathNotFound.Includes(result))
- {
- UnityEngine.Debug.Log($"目录 {path} 不存在");
- entrys = null;
- return false;
- }
- long entryCount = 0;
- nn.fs.Directory.GetEntryCount(ref entryCount, eHandle);
- nn.fs.DirectoryEntry[] entries = new nn.fs.DirectoryEntry[entryCount];
- long actualEntries = 0;
- nn.fs.Directory.Read(ref actualEntries, entries, eHandle, entryCount);
+ nn.fs.DirectoryHandle eHandle = new nn.fs.DirectoryHandle();
+ nn.Result result = nn.fs.Directory.Open(ref eHandle, path, OpenDirectoryMode.All);
+ if (nn.fs.FileSystem.ResultPathNotFound.Includes(result))
+ {
+ UnityEngine.Debug.Log($"目录 {path} 不存在");
+ entrys = null;
+ return false;
+ }
+ long entryCount = 0;
+ nn.fs.Directory.GetEntryCount(ref entryCount, eHandle);
+ nn.fs.DirectoryEntry[] entries = new nn.fs.DirectoryEntry[entryCount];
+ long actualEntries = 0;
+ nn.fs.Directory.Read(ref actualEntries, entries, eHandle, entryCount);
- List temp = new List();
- for (int i = 0; i < actualEntries; i++)
- {
- string singlePath = System.IO.Path.Combine(path, entries[i].name);
- temp.Add(singlePath);
- if (entries[i].entryType == EntryType.Directory && GetDirectoryEntrysFullRecursion(singlePath, out string[] singleEntryList))
- {
- temp.AddRange(singleEntryList);
- }
- }
- nn.fs.Directory.Close(eHandle);
- entrys = temp.ToArray();
- return true;
+ List temp = new List();
+ for (int i = 0; i < actualEntries; i++)
+ {
+ string singlePath = System.IO.Path.Combine(path, entries[i].name);
+ temp.Add(singlePath);
+ if (entries[i].entryType == EntryType.Directory && GetDirectoryEntrysFullRecursion(singlePath, out string[] singleEntryList))
+ {
+ temp.AddRange(singleEntryList);
+ }
+ }
+ nn.fs.Directory.Close(eHandle);
+ entrys = temp.ToArray();
+ return true;
#else
entrys = null;
return false;
#endif
- }
+ }
- public IEnumerable EnumerateFiles(string path, string searchPattern)
- {
+ public IEnumerable EnumerateFiles(string path, string searchPattern)
+ {
#if !UNITY_SWITCH || UNITY_EDITOR
- yield break;
+ yield break;
#else
// 将通配符转换为正则表达式(支持*和?)
var regexPattern = "^" +
@@ -500,10 +524,10 @@ public class AxiNSIO
}
}
#endif
- }
+ }
- public bool DeletePathFile(string filename)
- {
+ public bool DeletePathFile(string filename)
+ {
#if !UNITY_SWITCH
return false;
#else
@@ -515,32 +539,32 @@ public class AxiNSIO
UnityEngine.Switch.Notification.EnterExitRequestHandlingSection();
#endif
- if (CheckPathNotFound(filename))
- return false;
- nn.Result result;
- result = nn.fs.File.Delete(filename);
- if (result.IsSuccess() == false)
- {
- UnityEngine.Debug.LogError($"nn.fs.File.Delete 失败 {filename} : result=>{result.GetErrorInfo()}");
- return false;
- }
+ if (CheckPathNotFound(filename))
+ return false;
+ nn.Result result;
+ result = nn.fs.File.Delete(filename);
+ if (result.IsSuccess() == false)
+ {
+ UnityEngine.Debug.LogError($"nn.fs.File.Delete 失败 {filename} : result=>{result.GetErrorInfo()}");
+ return false;
+ }
#if UNITY_SWITCH && !UNITY_EDITOR
// End preventing the user from quitting the game while saving.
UnityEngine.Switch.Notification.LeaveExitRequestHandlingSection();
#endif
- return CommitSave();
+ return CommitSave();
#endif
- }
- public AxiNSWait_DeletePathFile DeletePathFileAsync(string filename)
- {
- var wait = new AxiNSWait_DeletePathFile(filename);
- AxiNS.instance.wait.AddWait(wait);
- return wait;
- }
- public bool DeletePathDir(string filename)
- {
+ }
+ public AxiNSWait_DeletePathFile DeletePathFileAsync(string filename)
+ {
+ var wait = new AxiNSWait_DeletePathFile(filename);
+ AxiNS.instance.wait.AddWait(wait);
+ return wait;
+ }
+ public bool DeletePathDir(string filename)
+ {
#if !UNITY_SWITCH
return false;
#else
@@ -551,31 +575,31 @@ public class AxiNSIO
UnityEngine.Switch.Notification.EnterExitRequestHandlingSection();
#endif
- if (CheckPathNotFound(filename))
- return false;
- nn.Result result;
- result = nn.fs.Directory.Delete(filename);
- if (result.IsSuccess() == false)
- {
- UnityEngine.Debug.LogError($"nn.fs.File.Delete 失败 {filename} : result=>{result.GetErrorInfo()}");
- return false;
- }
+ if (CheckPathNotFound(filename))
+ return false;
+ nn.Result result;
+ result = nn.fs.Directory.Delete(filename);
+ if (result.IsSuccess() == false)
+ {
+ UnityEngine.Debug.LogError($"nn.fs.File.Delete 失败 {filename} : result=>{result.GetErrorInfo()}");
+ return false;
+ }
#if UNITY_SWITCH && !UNITY_EDITOR
// End preventing the user from quitting the game while saving.
UnityEngine.Switch.Notification.LeaveExitRequestHandlingSection();
#endif
- return CommitSave();
+ return CommitSave();
#endif
- }
- public AxiNSWait_DeletePathDir DeletePathDirAsync(string filename)
- {
- var wait = new AxiNSWait_DeletePathDir(filename);
- AxiNS.instance.wait.AddWait(wait);
- return wait;
- }
- public bool DeletePathDirRecursively(string filename)
- {
+ }
+ public AxiNSWait_DeletePathDir DeletePathDirAsync(string filename)
+ {
+ var wait = new AxiNSWait_DeletePathDir(filename);
+ AxiNS.instance.wait.AddWait(wait);
+ return wait;
+ }
+ public bool DeletePathDirRecursively(string filename)
+ {
#if !UNITY_SWITCH
return false;
#else
@@ -586,37 +610,37 @@ public class AxiNSIO
UnityEngine.Switch.Notification.EnterExitRequestHandlingSection();
#endif
- if (CheckPathNotFound(filename))
- return false;
- nn.Result result;
- result = nn.fs.Directory.DeleteRecursively(filename);
- if (result.IsSuccess() == false)
- {
- UnityEngine.Debug.LogError($"nn.fs.File.Recursively 失败 {filename} : result=>{result.GetErrorInfo()}");
- return false;
- }
+ if (CheckPathNotFound(filename))
+ return false;
+ nn.Result result;
+ result = nn.fs.Directory.DeleteRecursively(filename);
+ if (result.IsSuccess() == false)
+ {
+ UnityEngine.Debug.LogError($"nn.fs.File.Recursively 失败 {filename} : result=>{result.GetErrorInfo()}");
+ return false;
+ }
#if UNITY_SWITCH && !UNITY_EDITOR
// End preventing the user from quitting the game while saving.
UnityEngine.Switch.Notification.LeaveExitRequestHandlingSection();
#endif
- return CommitSave();
+ return CommitSave();
#endif
- }
- public AxiNSWait_DeletePathDirRecursively DeletePathDirRecursivelyAsync(string filename)
- {
- var wait = new AxiNSWait_DeletePathDirRecursively(filename);
- AxiNS.instance.wait.AddWait(wait);
- return wait;
- }
+ }
+ public AxiNSWait_DeletePathDirRecursively DeletePathDirRecursivelyAsync(string filename)
+ {
+ var wait = new AxiNSWait_DeletePathDirRecursively(filename);
+ AxiNS.instance.wait.AddWait(wait);
+ return wait;
+ }
- ///
- /// 递归删除目录
- ///
- ///
- ///
- public bool DeleteRecursivelyPathDir(string filename)
- {
+ ///
+ /// 递归删除目录
+ ///
+ ///
+ ///
+ public bool DeleteRecursivelyPathDir(string filename)
+ {
#if !UNITY_SWITCH
return false;
#else
@@ -627,31 +651,31 @@ public class AxiNSIO
UnityEngine.Switch.Notification.EnterExitRequestHandlingSection();
#endif
- if (CheckPathNotFound(filename))
- return false;
- nn.Result result;
- result = nn.fs.Directory.DeleteRecursively(filename);
- if (result.IsSuccess() == false)
- {
- UnityEngine.Debug.LogError($"nn.fs.File.DeleteRecursively 失败 {filename} : result=>{result.GetErrorInfo()}");
- return false;
- }
+ if (CheckPathNotFound(filename))
+ return false;
+ nn.Result result;
+ result = nn.fs.Directory.DeleteRecursively(filename);
+ if (result.IsSuccess() == false)
+ {
+ UnityEngine.Debug.LogError($"nn.fs.File.DeleteRecursively 失败 {filename} : result=>{result.GetErrorInfo()}");
+ return false;
+ }
#if UNITY_SWITCH && !UNITY_EDITOR
// End preventing the user from quitting the game while saving.
UnityEngine.Switch.Notification.LeaveExitRequestHandlingSection();
#endif
- return CommitSave();
+ return CommitSave();
#endif
- }
+ }
- ///
- /// 递归删除情况
- ///
- ///
- ///
- public bool CleanRecursivelyPathDir(string filename)
- {
+ ///
+ /// 递归删除情况
+ ///
+ ///
+ ///
+ public bool CleanRecursivelyPathDir(string filename)
+ {
#if !UNITY_SWITCH
return false;
#else
@@ -662,26 +686,26 @@ public class AxiNSIO
UnityEngine.Switch.Notification.EnterExitRequestHandlingSection();
#endif
- if (CheckPathNotFound(filename))
- return false;
- nn.Result result;
- result = nn.fs.Directory.CleanRecursively(filename);
- if (result.IsSuccess() == false)
- {
- UnityEngine.Debug.LogError($"nn.fs.File.DeleteRecursively 失败 {filename} : result=>{result.GetErrorInfo()}");
- return false;
- }
+ if (CheckPathNotFound(filename))
+ return false;
+ nn.Result result;
+ result = nn.fs.Directory.CleanRecursively(filename);
+ if (result.IsSuccess() == false)
+ {
+ UnityEngine.Debug.LogError($"nn.fs.File.DeleteRecursively 失败 {filename} : result=>{result.GetErrorInfo()}");
+ return false;
+ }
#if UNITY_SWITCH && !UNITY_EDITOR
// End preventing the user from quitting the game while saving.
UnityEngine.Switch.Notification.LeaveExitRequestHandlingSection();
#endif
- return CommitSave();
+ return CommitSave();
#endif
- }
+ }
- public bool RenameDir(string oldpath, string newpath)
- {
+ public bool RenameDir(string oldpath, string newpath)
+ {
#if !UNITY_SWITCH
return false;
#else
@@ -692,146 +716,364 @@ public class AxiNSIO
UnityEngine.Switch.Notification.EnterExitRequestHandlingSection();
#endif
- if (CheckPathNotFound(oldpath))
- return false;
+ if (CheckPathNotFound(oldpath))
+ return false;
- nn.Result result;
- result = nn.fs.Directory.Rename(oldpath, newpath);
- if (result.IsSuccess() == false)
- {
- UnityEngine.Debug.LogError($"nn.fs.File.Rename 失败 {oldpath} to {newpath} : result=>{result.GetErrorInfo()}");
- return false;
- }
+ nn.Result result;
+ result = nn.fs.Directory.Rename(oldpath, newpath);
+ if (result.IsSuccess() == false)
+ {
+ UnityEngine.Debug.LogError($"nn.fs.File.Rename 失败 {oldpath} to {newpath} : result=>{result.GetErrorInfo()}");
+ return false;
+ }
#if UNITY_SWITCH && !UNITY_EDITOR
// End preventing the user from quitting the game while saving.
UnityEngine.Switch.Notification.LeaveExitRequestHandlingSection();
#endif
- return CommitSave();
+ return CommitSave();
#endif
- }
- bool EnsureParentDirectory(string filePath, bool bAutoCreateDir = true)
- {
+ }
+
+ bool CreateLoopDir(string path)
+ {
+ // 检查路径是否存在及其类型
+ nn.fs.EntryType entryType = 0;
+ nn.Result result;
+ List needcreatedirs = new List();
+ string node = path;
+ while (true)
+ {
+ if (string.IsNullOrEmpty(node) || node.EndsWith(":/"))
+ break;
+
+
+ if (!CheckPathNotFound(node))
+ needcreatedirs.Insert(0, node);
+ else
+ break;
+
+ result = nn.fs.FileSystem.GetEntryType(ref entryType, node);
+ if (!result.IsSuccess())
+ needcreatedirs.Insert(0, node);
+ else
+ break;//文件已存在
+
+ node = System.IO.Path.GetDirectoryName(node);
+ }
+
+ for (int i = 0; i < needcreatedirs.Count; i++)
+ {
+ UnityEngine.Debug.LogError($"需要创建的目录: {needcreatedirs[i]}");
+ }
+
+ for (int i = 0; i < needcreatedirs.Count; i++)
+ {
+ //result = nn.fs.Directory.Create(needcreatedirs[i]);
+ //if (!result.IsSuccess())
+ //{
+ // UnityEngine.Debug.LogError($"创建父目录失败: {result.GetErrorInfo()}");
+ // return false;
+ //}
+ //UnityEngine.Debug.Log($"父目录 {needcreatedirs[i]} 创建成功");
+ //CommitSave();
+ }
+
+ return false;
+ return true;
+ }
+
+
+ ///
+ /// 解析路径并获取其所有父级目录(从直接父目录到根目录),并排除存储设备挂载根节点(如"save:"或"sd:")。
+ /// 专为Switch平台设计,正确处理如"save:/"或"sd:/"开头的路径。
+ ///
+ /// 输入的绝对路径
+ /// 输出参数,解析出的最直接目录(文件所在目录或目录自身)
+ /// 输出参数,从直接父目录到挂载点下一级的列表(不包含挂载根节点)
+ /// 操作是否成功(路径格式基本有效)
+ public bool TryGetDirectoryAndParentsExcludingRoot(string inputPath, out string resolvedDirectory, out List parentDirectories)
+ {
+ // 捕获路径中包含非法字符引发的异常
+ UnityEngine.Debug.Log($"TryGetDirectoryAndParentsExcludingRoot->{inputPath}");
+ resolvedDirectory = null;
+ parentDirectories = new List();
+
+ if (string.IsNullOrWhiteSpace(inputPath))
+ {
+ UnityEngine.Debug.Log($"TryGetDirectoryAndParentsExcludingRoot->string.IsNullOrWhiteSpace({inputPath})==false");
+ return false;
+ }
+
+ string normalizedPath = inputPath.Replace('\\', '/').Trim(); // 统一使用正斜杠
+ UnityEngine.Debug.Log($"TryGetDirectoryAndParentsExcludingRoot->normalizedPath=>{normalizedPath}");
+ try
+ {
+ // 1. 判断路径类型并解析出最直接的目标目录
+ bool isLikelyFile = false;
+
+ if (normalizedPath.EndsWith("/"))
+ {
+ UnityEngine.Debug.Log($"TryGetDirectoryAndParentsExcludingRoot->normalizedPath.EndsWith(\"/\") == true");
+ resolvedDirectory = normalizedPath.TrimEnd('/');
+ }
+ else
+ {
+ int lastSeparatorIndex = normalizedPath.LastIndexOf('/');
+ UnityEngine.Debug.Log($"TryGetDirectoryAndParentsExcludingRoot->lastSeparatorIndex->{lastSeparatorIndex}");
+ string lastPart = (lastSeparatorIndex >= 0) ? normalizedPath.Substring(lastSeparatorIndex + 1) : normalizedPath;
+
+ if (string.IsNullOrEmpty(lastPart) || lastPart.Equals("..") || !lastPart.Contains("."))
+ {
+ UnityEngine.Debug.Log($"TryGetDirectoryAndParentsExcludingRoot->step1");
+ resolvedDirectory = normalizedPath;
+ }
+ else
+ {
+ UnityEngine.Debug.Log($"TryGetDirectoryAndParentsExcludingRoot->step2");
+ isLikelyFile = true;
+ UnityEngine.Debug.Log($"TryGetDirectoryAndParentsExcludingRoot->lastSeparatorIndex=>{lastSeparatorIndex}");
+ if (lastSeparatorIndex >= 0)
+ {
+ resolvedDirectory = normalizedPath.Substring(0, lastSeparatorIndex);
+ }
+ else
+ {
+ resolvedDirectory = normalizedPath; // 可能是根目录下的文件,但这种情况在Switch特殊路径中较少
+ }
+ }
+ }
+
+ UnityEngine.Debug.Log($"TryGetDirectoryAndParentsExcludingRoot->resolvedDirectory=>{resolvedDirectory}");
+ if (string.IsNullOrEmpty(resolvedDirectory))
+ {
+ UnityEngine.Debug.LogError($"TryGetDirectoryAndParentsExcludingRoot->string.IsNullOrEmpty(resolvedDirectory) == false");
+ return false;
+ }
+
+ UnityEngine.Debug.Log($"TryGetDirectoryAndParentsExcludingRoot->step3");
+ // 2. 提取并检查挂载根节点(如 "save:" 或 "sd:")
+ string mountRoot = null;
+ int colonSlashIndex = resolvedDirectory.IndexOf(":/");
+ if (colonSlashIndex > 0)
+ {
+ mountRoot = resolvedDirectory.Substring(0, colonSlashIndex + 1); // 例如 "save:"
+ }
+ UnityEngine.Debug.Log($"TryGetDirectoryAndParentsExcludingRoot->mountRoot=>{mountRoot}");
+
+ // 检查挂载状态
+ if (!IsMountPointAccessible(mountRoot + "/"))
+ {
+ UnityEngine.Debug.LogError($"挂载点 {mountRoot + "/"} 未挂载,无法操作路径 {inputPath}");
+ return false;
+ }
+
+ UnityEngine.Debug.Log($"TryGetDirectoryAndParentsExcludingRoot->step4");
+ // 3. 手动分割路径,收集父目录,并在到达挂载根节点时停止
+ string currentPath = resolvedDirectory;
+ UnityEngine.Debug.Log($"TryGetDirectoryAndParentsExcludingRoot->currentPath=>{currentPath}");
+ while (!string.IsNullOrEmpty(currentPath))
+ {
+ UnityEngine.Debug.Log($"TryGetDirectoryAndParentsExcludingRoot->step5");
+ // 检查当前路径是否已经是挂载根节点(例如 "save:")
+ if (mountRoot != null && currentPath.Equals(mountRoot, StringComparison.OrdinalIgnoreCase))
+ {
+ break; // 停止添加,不将挂载根节点加入父目录列表
+ }
+
+ parentDirectories.Add(currentPath); // 将当前层级的路径加入列表
+
+ int lastSlashIndex = currentPath.LastIndexOf('/');
+ if (lastSlashIndex < 0)
+ {
+ break; // 没有分隔符了,跳出循环
+ }
+
+ string nextParent = currentPath.Substring(0, lastSlashIndex);
+
+ // 检查下一级父目录是否就是挂载根节点(例如 "save:"),如果是,则停止
+ if (mountRoot != null && nextParent.Equals(mountRoot, StringComparison.OrdinalIgnoreCase))
+ {
+ // 可以选择是否将 mountRoot 加入列表,这里根据需求不加入
+ break;
+ }
+
+ currentPath = nextParent;
+ }
+ UnityEngine.Debug.Log($"TryGetDirectoryAndParentsExcludingRoot->step6 True Return");
+
+ return true;
+ }
+ catch (ArgumentException ex)
+ {
+ // 捕获路径中包含非法字符引发的异常
+ UnityEngine.Debug.LogError($"路径中包含非法字符: {ex.Message}");
+ return false;
+ }
+ }
+
+ bool EnsureParentDirectory(string filePath, bool bAutoCreateDir = true)
+ {
#if !UNITY_SWITCH
return false;
#else
- // 参数校验
- if (string.IsNullOrEmpty(filePath))
- {
- UnityEngine.Debug.LogError($"无效参数:filePath={filePath}");
- return false;
- }
+ //// 参数校验
+ //if (string.IsNullOrEmpty(filePath))
+ //{
+ // UnityEngine.Debug.LogError($"无效参数:filePath={filePath}");
+ // return false;
+ //}
- // 提取路径前缀(如 save:/、sd:/)
- int prefixEndIndex = filePath.IndexOf(":/");
- if (prefixEndIndex == -1)
- {
- UnityEngine.Debug.LogError($"文件路径 {filePath} 格式无效,未找到 ':/' 前缀");
- return false;
- }
- string pathPrefix = filePath.Substring(0, prefixEndIndex + 2); // 提取前缀,例如 "save:/"
- string relativePath = filePath.Substring(prefixEndIndex + 2); // 移除前缀,得到相对路径
+ //// 提取路径前缀(如 save:/、sd:/)
+ //int prefixEndIndex = filePath.IndexOf(":/");
+ //if (prefixEndIndex == -1)
+ //{
+ // UnityEngine.Debug.LogError($"文件路径 {filePath} 格式无效,未找到 ':/' 前缀");
+ // return false;
+ //}
+ //string pathPrefix = filePath.Substring(0, prefixEndIndex + 2); // 提取前缀,例如 "save:/"
+ //string relativePath = filePath.Substring(prefixEndIndex + 2); // 移除前缀,得到相对路径
- // 检查挂载状态
- if (!IsMountPointAccessible(pathPrefix))
- {
- UnityEngine.Debug.LogError($"挂载点 {pathPrefix} 未挂载,无法操作路径 {filePath}");
- return false;
- }
+ //// 检查挂载状态
+ //if (!IsMountPointAccessible(pathPrefix))
+ //{
+ // UnityEngine.Debug.LogError($"挂载点 {pathPrefix} 未挂载,无法操作路径 {filePath}");
+ // return false;
+ //}
- // 提取父目录路径
- string directoryPath = System.IO.Path.GetDirectoryName(relativePath); // 获取父目录相对路径
- if (string.IsNullOrEmpty(directoryPath))
- {
- UnityEngine.Debug.Log($"文件路径 {filePath} 无需创建父目录(位于根目录)");
- return true; // 根目录无需创建
- }
+ //// 提取父目录路径
+ //string directoryPath = System.IO.Path.GetDirectoryName(relativePath); // 获取父目录相对路径
+ //UnityEngine.Debug.Log($"提取 {relativePath} 的 父级路径:{directoryPath}");
+ //if (string.IsNullOrEmpty(directoryPath))
+ //{
+ // UnityEngine.Debug.Log($"文件路径 {filePath} 无需创建父目录(位于根目录)");
+ // return true; // 根目录无需创建
+ //}
- string fullDirectoryPath = $"{pathPrefix}{directoryPath}"; // 拼接完整父目录路径
- UnityEngine.Debug.Log($"检查父目录: {fullDirectoryPath}");
+ //string fullDirectoryPath = $"{pathPrefix}{directoryPath}"; // 拼接完整父目录路径
- // 检查路径是否存在及其类型
- nn.fs.EntryType entryType = 0;
- nn.Result result = nn.fs.FileSystem.GetEntryType(ref entryType, fullDirectoryPath);
- if (!result.IsSuccess() && nn.fs.FileSystem.ResultPathNotFound.Includes(result))
- {
- if (bAutoCreateDir)
- {
- // 路径不存在,尝试创建
- UnityEngine.Debug.Log($"父目录 {fullDirectoryPath} 不存在,尝试创建 (判断依据 result=>{result.ToString()})");
- result = nn.fs.Directory.Create(fullDirectoryPath);
- if (!result.IsSuccess())
- {
- UnityEngine.Debug.LogError($"创建父目录失败: {result.GetErrorInfo()}");
- return false;
- }
- UnityEngine.Debug.Log($"父目录 {fullDirectoryPath} 创建成功");
- return true;
- }
- return false;
- }
- else if (result.IsSuccess() && entryType != nn.fs.EntryType.Directory)
- {
- // 路径存在,但不是目录
- UnityEngine.Debug.LogError($"路径 {fullDirectoryPath} 已存在,但不是目录");
- return false;
- }
- else if (!result.IsSuccess())
- {
- // 其他错误
- UnityEngine.Debug.LogError($"检查父目录失败: {result.GetErrorInfo()}");
- return false;
- }
- // 路径存在且是目录
- UnityEngine.Debug.Log($"父目录 {fullDirectoryPath} 已存在且有效");
- return true;
+
+ if (!TryGetDirectoryAndParentsExcludingRoot(filePath, out string fullDirectoryPath, out List parentDirectories))
+ {
+ UnityEngine.Debug.LogError($"TryGetDirectoryAndParentsExcludingRoot 操作失败:{filePath}");
+ return false;
+ }
+
+ UnityEngine.Debug.Log($"检查父目录: {fullDirectoryPath}");
+
+ // 检查路径是否存在及其类型
+ nn.fs.EntryType entryType = 0;
+ nn.Result result = nn.fs.FileSystem.GetEntryType(ref entryType, fullDirectoryPath);
+ if (!result.IsSuccess() && nn.fs.FileSystem.ResultPathNotFound.Includes(result))
+ {
+ if (bAutoCreateDir)
+ {
+ // 路径不存在,尝试创建
+ UnityEngine.Debug.Log($"父目录 {fullDirectoryPath} 不存在,尝试创建 (判断依据 result=>{result.ToString()})");
+
+ for (int i = parentDirectories.Count - 1; i >= 0; i--)
+ {
+ UnityEngine.Debug.Log($">>待检查目录: {parentDirectories[i]}");
+ }
+
+ for (int i = parentDirectories.Count - 1; i >= 0; i--)
+ {
+ string dir = parentDirectories[i];
+ if (CheckPathNotFound(dir))
+ {
+ UnityEngine.Debug.Log($"需要创建的目录: {dir}");
+ result = nn.fs.Directory.Create(dir);
+ if (!result.IsSuccess())
+ {
+ UnityEngine.Debug.LogError($"创建父 {dir} 目录失败: {result.GetErrorInfo()}");
+ return false;
+ }
+ UnityEngine.Debug.Log($"父目录 {dir} 创建成功");
+ //CommitSave();
+ }
+ else
+ {
+ UnityEngine.Debug.Log($"目录已存在,无需创建: {dir}");
+ }
+ }
+
+ //result = nn.fs.Directory.Create(fullDirectoryPath);
+ //if (!result.IsSuccess())
+ //{
+ // UnityEngine.Debug.LogError($"创建父目录失败: {result.GetErrorInfo()}");
+ // return false;
+ //}
+
+ //if (!CreateLoopDir(fullDirectoryPath))
+ // return false;
+
+ UnityEngine.Debug.Log($"父目录 {fullDirectoryPath} 创建成功");
+ return true;
+ }
+ return false;
+ }
+ else if (result.IsSuccess() && entryType != nn.fs.EntryType.Directory)
+ {
+ // 路径存在,但不是目录
+ UnityEngine.Debug.LogError($"路径 {fullDirectoryPath} 已存在,但不是目录");
+ return false;
+ }
+ else if (!result.IsSuccess())
+ {
+ // 其他错误
+ UnityEngine.Debug.LogError($"检查父目录失败: {result.GetErrorInfo()}");
+ return false;
+ }
+ // 路径存在且是目录
+ UnityEngine.Debug.Log($"父目录 {fullDirectoryPath} 已存在且有效");
+ return true;
#endif
- }
- ///
- /// 检查指定挂载点是否可访问
- ///
- /// 路径前缀,例如 "save:/" 或 "sd:/"
- /// 挂载点是否可访问
- bool IsMountPointAccessible(string pathPrefix)
- {
+ }
+ ///
+ /// 检查指定挂载点是否可访问
+ ///
+ /// 路径前缀,例如 "save:/" 或 "sd:/"
+ /// 挂载点是否可访问
+ bool IsMountPointAccessible(string pathPrefix)
+ {
#if !UNITY_SWITCH
return false;
#else
- if (string.IsNullOrEmpty(pathPrefix))
- {
- UnityEngine.Debug.LogError($"无效挂载点: {pathPrefix}");
- return false;
- }
+ if (string.IsNullOrEmpty(pathPrefix))
+ {
+ UnityEngine.Debug.LogError($"无效挂载点: {pathPrefix}");
+ return false;
+ }
- // 根据前缀判断挂载点类型并检查挂载状态
- if (pathPrefix == $"{save_name}:/")
- {
- if (!AxiNS.instance.mount.SaveIsMount)
- {
- UnityEngine.Debug.LogError($"{save_name}:/ 未挂载");
- return false;
- }
- return true;
- }
- else if (pathPrefix == "sd:/")
- {
- long freeSpace = 0;
- // 检查 SD 卡挂载状态(示例,需根据实际实现调整)
- nn.Result result = nn.fs.FileSystem.GetFreeSpaceSize(ref freeSpace, "sd:/");
- if (!result.IsSuccess())
- {
- UnityEngine.Debug.LogError($"sd:/ 未挂载或无法访问: {result.GetErrorInfo()}");
- return false;
- }
- return true;
- }
- else
- {
- UnityEngine.Debug.LogWarning($"未知挂载点 {pathPrefix},假定已挂载");
- return true; // 其他挂载点需根据实际需求实现
- }
+ // 根据前缀判断挂载点类型并检查挂载状态
+ if (pathPrefix == $"{save_name}:/")
+ {
+ if (!AxiNS.instance.mount.SaveIsMount)
+ {
+ UnityEngine.Debug.LogError($"{save_name}:/ 未挂载");
+ return false;
+ }
+ return true;
+ }
+ else if (pathPrefix == "sd:/")
+ {
+ long freeSpace = 0;
+ // 检查 SD 卡挂载状态(示例,需根据实际实现调整)
+ nn.Result result = nn.fs.FileSystem.GetFreeSpaceSize(ref freeSpace, "sd:/");
+ if (!result.IsSuccess())
+ {
+ UnityEngine.Debug.LogError($"sd:/ 未挂载或无法访问: {result.GetErrorInfo()}");
+ return false;
+ }
+ return true;
+ }
+ else
+ {
+ UnityEngine.Debug.LogWarning($"未知挂载点 {pathPrefix},假定已挂载");
+ return true; // 其他挂载点需根据实际需求实现
+ }
#endif
- }
+ }
}