问题描述
我正在使用Unity开发HoloLens 2的UWP应用。我想写入日志文件(以记录用户交互),然后在以后检索该文件。我不希望用户必须选择文件位置。
以下代码在Desktop UWP应用程序上有效(来自相同代码和相同Unity项目的输出)。它不适用于HoloLens,而是引发“未经授权”异常。如何在HoloLens上写入文件?以后我在哪里可以找到该文件?
public class Logger : MonoBehavIoUr
{
StreamWriter logFileWriter;
// Start is called before the first frame update
void Start()
{
string fileName = "mydatalog.csv";
// Creates a file in the default location:
// "build\bin\x64\Release\Appx" on Desktop
this.logFileWriter = new StreamWriter(fileName);
}
void Update()
{
string record = // Stuff here...
if (this.logFileWriter != null)
{
this.logFileWriter.WriteLine(record);
}
}
}
解决方法
为什么不尝试设置文件路径以写入Application.persistentDataPath
?在Unity's docs中,对于Windows应用程序,该路径指向
%userprofile%\AppData\Local\Packages\<productname>\LocalState
所以这是以后在桌面上查找文件的路径。
在与Hololens合作时,我曾经在那儿写持久性数据。然后,通过桌面上的Hololens门户,我可以导航到我编写的文件。
我还没有使用Hololens 2,但是我认为这个过程不会有很大的不同。
,可以通过代码访问 HoloLens 设备中的 Documents 文件夹,而无需使用文件选择器。这是我创建的用于读取文件的帮助文件,我没有测试过写入但应该是类似的。
在visual studio中,您可能会看到#if WINDOWS_UWP 中的部分变灰,以修复从Assembly-CSharp 到Assembly-CSharp.Player 的更改 (How to Change It)
using UnityEngine;
using System.IO;
using System;
using System.Collections.Generic;
using System.Threading.Tasks;
public class FileHelper : MonoBehaviour
{
public static string path;
private void Start()
{
path = Application.streamingAssetsPath;
#if WINDOWS_UWP
Task pathTask = new Task(
async () =>
{
try
{
var folders = await Windows.Storage.KnownFolders.DocumentsLibrary.GetFoldersAsync();
if (folders != null && folders.Count > 0) FileHelper.path = folders[0].Path.Substring(0,folders[0].Path.LastIndexOfAny(new char[2] { '/','\\' }));
}
catch (Exception e)
{
Debug.LogError("Failed to locate documents folder!");
}
});
pathTask.Start();
#endif
}
public static string ReadFile(string filename)
{
string content = string.Empty;
if (System.IO.File.Exists(Path.Combine(path,filename)))
{
try
{
StreamReader reader = new StreamReader(Path.Combine(path,filename));
if (reader == null) return string.Empty;
content = reader.ReadToEnd();
reader.Close();
}
catch (Exception) { }
}
return content;
}
}
这不会单独工作,因为您必须在构建时编辑包清单文件以包含访问文档文件夹的正确权限。要在 MRTK 构建窗口中完成此操作,您首先单击“构建 Unity 项目”。
在我们构建 APPX 包之前构建项目后,我们必须编辑清单文件,该文件位于:
您的项目/临时/StagingArea/Package.appxmanifest
使用 Visual Studio Code 等代码编辑器打开文件,我们必须添加 docuentsLibrary 的功能,并包含我们将使用的文件类型作为扩展名。要添加扩展,您必须将它放在应用程序选择中的 VisualElements 结束标记下。您可以根据需要添加任意数量的文件类型,目前我包括“.json”和“.data”文件。
这是在添加功能和 filetpye 说明符之前我将编辑的 mainifest 文件的部分:(第 16 行到第 35 行)
<Applications>
<Application Id="App" Executable="$targetnametoken$.exe" EntryPoint="ARIVE.App">
<uap:VisualElements DisplayName="HoloLens File Reader" Square150x150Logo="Assets\Square150x150Logo.png" Square44x44Logo="Assets\Square44x44Logo.png" Description="Template_3D" BackgroundColor="transparent">
<uap:DefaultTile Wide310x150Logo="Assets\Wide310x150Logo.png" />
<uap:SplashScreen Image="Assets\SplashScreen.png" BackgroundColor="#FFFFFF" />
<uap:InitialRotationPreference>
<uap:Rotation Preference="landscape" />
<uap:Rotation Preference="landscapeFlipped" />
<uap:Rotation Preference="portrait" />
<uap:Rotation Preference="portraitFlipped" />
</uap:InitialRotationPreference>
</uap:VisualElements>
</Application>
</Applications>
<Capabilities>
<uap2:Capability Name="spatialPerception" />
<DeviceCapability Name="microphone" />
<DeviceCapability Name="location" />
<DeviceCapability Name="gazeinput" />
</Capabilities>
这是更新的版本:(第 16 行到第 47 行)
<Applications>
<Application Id="App" Executable="$targetnametoken$.exe" EntryPoint="ARIVE.App">
<uap:VisualElements DisplayName="HoloLens File Reader" Square150x150Logo="Assets\Square150x150Logo.png" Square44x44Logo="Assets\Square44x44Logo.png" Description="Template_3D" BackgroundColor="transparent">
<uap:DefaultTile Wide310x150Logo="Assets\Wide310x150Logo.png" />
<uap:SplashScreen Image="Assets\SplashScreen.png" BackgroundColor="#FFFFFF" />
<uap:InitialRotationPreference>
<uap:Rotation Preference="landscape" />
<uap:Rotation Preference="landscapeFlipped" />
<uap:Rotation Preference="portrait" />
<uap:Rotation Preference="portraitFlipped" />
</uap:InitialRotationPreference>
</uap:VisualElements>
<Extensions>
<uap:Extension Category="windows.fileTypeAssociation">
<uap:FileTypeAssociation Name="waypoint">
<uap:DisplayName>waypoint list</uap:DisplayName>
<uap:SupportedFileTypes>
<uap:FileType>.json</uap:FileType>
<uap:FileType>.data</uap:FileType>
</uap:SupportedFileTypes>
</uap:FileTypeAssociation>
</uap:Extension>
</Extensions>
</Application>
</Applications>
<Capabilities>
<uap:Capability Name="documentsLibrary" />
<uap2:Capability Name="spatialPerception" />
<DeviceCapability Name="microphone" />
<DeviceCapability Name="location" />
<DeviceCapability Name="gazeinput" />
</Capabilities>
现在您已经更新了清单,您可以返回 Unity 并单击 MRTK 构建窗口中的“构建 APPX”按钮。