Convert System.IO to UnityEngine.Windows

I have never used UnityEngine.Windows and it seems it lacks a lot of functionality of System.IO. Can Anyone anyone explain how to convert from System.IO to UnityEngine.Windows? I’ve read a lot of threads on it but I think the way my save system is set up is making it difficult for me.

        string subDir = Path.Combine(Application.persistentDataPath, "Saves"); //Path to where save data is stored.
        if (!Directory.Exists(subDir))
        {
            Directory.CreateDirectory(Application.persistentDataPath + "/Saves"); //If the subDir doesn't exist, create it.
        }
        foreach (string file in Directory.GetFiles(subDir)) //foreach file in the subdir
        {
            if (Path.GetFileNameWithoutExtension(file) != "Temp") //so long as the file isn't named temp
            {
//spawns buttons for every file, clicking the button loads the file

Like what is the equivalent of Path.Combine, or Directory.GetDirectories, as these are not present in UnityEngine.Windows.

I really appreciate any help, Thanks.

UnityEngine.Windows is an Unity specific namespace and has no relation to the .NET System.IO namespace.

The UnityEngine.Windows contains a set of Windows Specific APIs, primarily for Speech Recognition and WebCam. It’s similar to the UnityEngine.iOS and UnityEngine.Android namespaces, which contain platform specific classes.

The File and Directory classes are only there (I believe) to support CrashReporting for UWP. There’s no reason to use these APIs for general file I/O.

I must have misread something, I thought that System.IO doesn’t work on WUP because it blocks access to files/directories outside the space it allocates for the application and there was a windows specific library that had to be used instead? That part of the code I linked doesn’t work on WUP but works fine on Linux/mac/windows.

All the System.IO classes should be available on UWP (at least all the classes implemented in Mono).

You’re correct that UWP does restrict which locations you can read/write from, but all System.IO APIs will work so long as you use them in the proper directories. For example, doing this in UWP
File.Create(@"C:\MyFile.txt"); will throw a “Access Denied” exception.

Use the Unity Application.*Path APIs to retrieve file paths that your UWP app can safely access. Specifically, the Application.persistantDataPath where your UWP app has full access to read/write files and save data.

For example: File.Create(Path.Combine(Application.persistantDataPath, "MyFile.txt")); should work.

1 Like

Thank you this helped clear things up a lot, I found the issue to actually be this block of code below.

It seems like it’s going to the persistentDataPath to me, but maybe easy save 3 is doing something I’m not aware of or I’m misusing Path.Combine.

            string subDir = Path.Combine(Application.persistentDataPath, "Saves");
            string path = Path.Combine(subDir, curSaveSelected);
            if (!File.Exists(path))
            {
                ES3.Save<string>("FileName", curSaveSelected, path);
                SaveManager.curSaveFileName = Path.GetFileNameWithoutExtension(path);
                LoadSaveFiles();
            }
            else
            {
                Debug.LogError("Save file name already in use.");
            }

5843716--620515--Untitled.png

Thanks for the help, it works now it was my string = Path.Combines.

I decided to stop using the strings and to navigate with just Path.Combine instead.

if (curSaveSelected != null && curSaveSelected != "")
        {
            if (!File.Exists(Path.Combine(Application.persistentDataPath, curSaveSelected)))
            {
                ES3.Save<string>("FileName", curSaveSelected);
                SaveManager.curSaveFileName = Path.GetFileNameWithoutExtension(Path.Combine(Application.persistentDataPath, curSaveSelected));
                LoadSaveFiles();
            }
            else
            {
                Debug.LogError("Save file name already in use.");
            }

Strange, I don’t see anything wrong with the original set of code; the Path.Combine calls look correct from what I can see. The updated code doesn’t do anything different than the first (still producing an absolute path string), except that you left off the “Saves” folder name.

Hmmm…OK I think I see the problem: System.IO.Directory.CreateDirectory is trying to recursively create the entire directory path all the way down to root, even though most of the path already exists (only needs to create “Saves”). So, when it tries to create C:\User it hits the AccessDenied exception.

I think this occurs because E3S is calling CreateDirectory on the entire path. Instead, try creating your sub-directory first and then call into E3S:

string subDir = Path.Combine(Application.persistentDataPath, "Saves");
Directory.CreateDirectory(subDir);
string path = Path.Combine(subDir, curSaveSelected);
...
1 Like

I reset everything and did as you suggested here instead and it worked.

Thanks for the help :slight_smile: