Check if a file exists in the project in WinRT

10,646

Solution 1

You could use GetFilesAsync from here to enumerate the existing files. This seems to make sense considering you have multiple files which might not exist.

Gets a list of all files in the current folder and its sub-folders. Files are filtered and sorted based on the specified CommonFileQuery.

var folder = await StorageFolder.GetFolderFromPathAsync("Assets/MyImages/");
var files = await folder.GetFilesAsync(CommonFileQuery.OrderByName);
var file = files.FirstOrDefault(x => x.Name == "fileName");
if (file != null)
{
    //do stuff
}

Edit:

As @Filip Skakun pointed out, the resource manager has a resource mapping on which you can call ContainsKey which has the benefit of checking for qualified resources as well (i.e. localized, scaled etc).

Edit 2:

Windows 8.1 introduced a new method for getting files and folders:

var result = await ApplicationData.Current.LocalFolder.TryGetItemAsync("fileName") as IStorageFile;
if (result != null)
    //file exists
else
    //file doesn't exist

Solution 2

There's two ways you can handle it.

1) Catch the FileNotFoundException when trying to get the file:

 Windows.Storage.StorageFolder installedLocation = 
     Windows.ApplicationModel.Package.Current.InstalledLocation;
 try
 {
     // Don't forget to decorate your method or event with async when using await
     var file = await installedLocation.GetFileAsync(fileName);
     // Exception wasn't raised, therefore the file exists
     System.Diagnostics.Debug.WriteLine("We have the file!");
 }
 catch (System.IO.FileNotFoundException fileNotFoundEx)
 {
     System.Diagnostics.Debug.WriteLine("File doesn't exist. Use default.");
 }
 catch (Exception ex)
 {
     // Handle unknown error
 }

2) as mydogisbox recommends, using LINQ. Although the method I tested is slightly different:

 Windows.Storage.StorageFolder installedLocation =
     Windows.ApplicationModel.Package.Current.InstalledLocation;
 var files = await installedLocation.GetFilesAsync(CommonFileQuery.OrderByName);
 var file = files.FirstOrDefault(x => x.Name == fileName);
 if (file != null)
 {
    System.Diagnostics.Debug.WriteLine("We have the file!");
 }
 else
 {
    System.Diagnostics.Debug.WriteLine("No File. Use default.");
 }

Solution 3

BitmapImage has an ImageFailed event that fires if the image can't be loaded. This would let you try to load the original image, and then react if it's not there.

Of course, this requires that you instantiate the BitmapImage yourself, rather than just build the Uri.

Share:
10,646
Paul Michaels
Author by

Paul Michaels

I've been a programmer for most of my life. I have an interest in games, mobile and tablet development, along with message queuing, and pretty much anything that provides an elegant solution to a problem, technical or otherwise. I like learning new technology and finding new ways to use the old. I blog about my experiences here. You can read about me, or contact me on Linked in here.

Updated on June 09, 2022

Comments

  • Paul Michaels
    Paul Michaels almost 2 years

    I have a WinRT Metro project which displays images based on a selected item. However, some of the images selected will not exist. What I want to be able to do is trap the case where they don't exist and display an alternative.

    Here is my code so far:

    internal string GetMyImage(string imageDescription)
    {
        string myImage = string.Format("Assets/MyImages/{0}.jpg", imageDescription.Replace(" ", ""));
    
        // Need to check here if the above asset actually exists
    
        return myImage;
    }
    

    Example calls:

    GetMyImage("First Picture");
    GetMyImage("Second Picture");
    

    So Assets/MyImages/SecondPicture.jpg exists, but Assets/MyImages/FirstPicture.jpg does not.

    At first I thought of using the WinRT equivalent of File.Exists(), but there doesn't appear to be one. Without having to go to the extent of trying to open the file and catching an error, can I simply check if either the file exists, or the file exists in the project?