在 UWP 中使用 Windows.Storage 命名空间获取内部驱动器

Get Internal Drives Using Windows.Storage Namespace in UWP

花了一些时间阅读 Windows.Storage 类 和方法后,我有点震惊地发现没有简单的方法来检索磁盘上的内部驱动器列表使用 UWP 的机器。我找到了这样的示例:How to get logical drives names in Windows 10?,但这仅提供可移动驱动器(闪存驱动器、DVD 驱动器等)。

我知道我可以允许用户 select 一个文件夹,这将为我提供 selected 驱动器的句柄,但它看起来很笨重,因为我希望用户能够 运行 我的软件并扫描 PC 上的内部磁盘,而无需每次都重新 select 驱动器。

我已将 broadFileSystemAccess 属性添加到清单中,因此可以访问磁盘,但我无法调用方法来获取内部驱动器。作为解决方法,我编写了以下方法。

public List<StorageFolder> GetInternalDrives()
{
    string driveLetters = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";
    int driveLettersLen = driveLetters.Length;
    string removableDriveLetters = "";
    string driveLetter;

    List<StorageFolder> drives = new List<StorageFolder>();
    StorageFolder removableDevices = KnownFolders.RemovableDevices;
    IReadOnlyList<StorageFolder> folders = Task.Run<IReadOnlyList<StorageFolder>>(async () => await removableDevices.GetFoldersAsync()).Result;

    foreach (StorageFolder removableDevice in folders)
    {
        if (string.IsNullOrEmpty(removableDevice.Path)) continue;
        driveLetter = removableDevice.Path.Substring(0, 1).ToUpper();
        if (driveLetters.IndexOf(driveLetter) > -1) removableDriveLetters += driveLetter;
    }

    for (int curDrive = 0; curDrive < driveLettersLen; curDrive++)
    {
        driveLetter = driveLetters.Substring(curDrive, 1);
        if (removableDriveLetters.IndexOf(driveLetter) > -1) continue;

        try
        {
            StorageFolder drive = Task.Run<StorageFolder>(async () => await StorageFolder.GetFolderFromPathAsync(driveLetter + ":")).Result;
            drives.Add(drive);
        }
        catch (System.AggregateException) { }

    }

    return drives;
}

下面是调用 GetInternalDrives 的示例:

List<StorageFolder> drives = GetInternalDrives();
panScanParams.Children.Clear();
foreach (StorageFolder drive in drives)
{
    CheckBox cb = new CheckBox();
    cb.Content = drive.DisplayName;
    cb.IsChecked = true;
    panScanParams.Children.Add(cb);
}

虽然代码只为应用程序的一个实例调用一次,但我对代码一点也不满意。当它为字母表中的每个字母调用 StorageFolder.GetFolderFromPathAsync 时,它在我的机器上崩溃了 20 多次。编写您预计会失败的代码并处理异常似乎是不好的做法。但是由于没有合适的选择,我不知道还有什么选择。

有没有人解决过同样的问题,如果有,您是如何解决的?

或者您可以尝试使用此代码 var driveLetters = DriveInfo.GetDrives().Select(x => x.RootDirectory.Root).ToList().OrderBy(x => x.Root.FullName).ToList(); 来获取驱动器,而不是使用 StorageFolder 方法逐一排除。之后,遍历结果列表并转换为 StorageFolder。下面的代码我没有删除可移动驱动器。

var driveLetters = DriveInfo.GetDrives().Select(x => x.RootDirectory.Root).ToList().OrderBy(x => x.Root.FullName).ToList();
List<StorageFolder> drives = new List<StorageFolder>();
foreach (var driveInfo in driveLetters)
{
    String a = driveInfo.ToString();
    StorageFolder drive = Task.Run<StorageFolder>(async () => await StorageFolder.GetFolderFromPathAsync(a)).Result;
    drives.Add(drive);
}