绑定Windows Store App中硬盘的数据

时间:2014-03-04 21:09:44

标签: c# .net xaml data-binding windows-store-apps

使用c#,VS 2013,Windows应用商店

我有一些关于某些事件的信息的Json文件,在这个文件中,用户可以存储一些数据,以及其中一个数据 - 事件的图像路径,例如:

{"Events":
[
  {
    "UniqueId": "Day-1-Item-1",
    "Name": "Item Title: 1",
    "Place": "Item Subtitle: 1",
    "Description": "Event 1",
    "Start" : "2,25,2014,2,14",
    "End" : "2,25,2014,16,44",
    "ImagePath" : "Assets/appbar.calendar.png"
  },
  {
    "UniqueId": "Day-1-Item-2",
    "Name": "Item Title: 1",
    "Place": "Item Subtitle: 1",
    "Description": "Event 1",
    "Start" : "2,25,2014,2,14",
    "End" : "2,25,2014,16,44",
    "ImagePath" : "D:\\Pictures\\Abstract\\8.jpg"
  }
]

}

所以我将所有这些信息绑定到UI(使用XAML)并获得如下图所示的内容:

enter image description here

所以,对于那些我从项目中的Assets文件夹中放入pic的项目(平均"ImagePath" : "Assets/appbar.calendar.png"),我得到了正确的结果(在pic的日历上),但对于事件,我从硬盘中选择pic - 我什么都没得到

问题:是否可以将UI绑定到HardDrive中的数据?或者我需要在App的assets文件夹(或LocalState文件夹)中创建一些pic副本?


修改

所以现在我有下一个:

    public object Convert(object value, Type targetType, object parameter, string language)
    {
        string filePath = value.ToString(); //get path to picture
        BitmapImage image = new BitmapImage(); //create bitmap image blank

        if (filePath.Contains("Assets")) //if standart picture
        {
            return LoadImageFromAssetsLibrary(image);
        }
        else
        {
            return LoadImageFromString(image, filePath);
        }
    }

    public object ConvertBack(object value, Type targetType, object parameter, string language)
    {
        throw new NotImplementedException();
    }

    private async Task<ImageSource> LoadImageFromString(BitmapImage image, string path)
    {
        StorageFolder folder = KnownFolders.PicturesLibrary; //get folder
        StorageFile file = await folder.GetFileAsync(path); //find and read file
        //set source of file to image
        using (IRandomAccessStream stream = await file.OpenAsync(FileAccessMode.Read))
        {
            await image.SetSourceAsync(stream);
        }

        return ...// i dont know how to return ImageSource from image that i create in code above
    }

所以我有点堆叠 - 如何从图像返回ImageSource,尝试(ImageSource)image但得到(targetType - ImageSource):

enter image description here


编辑2

经过小的更改(从上次更新)后,从app文件夹中获取的图片可以通过转换器显示,但是从图片库中显示 - 不 - 认为问题是有访问权限...

enter image description here

已更改:

 public object Convert(object value, Type targetType, object parameter, string language)
    {
        string filePath = value.ToString(); //get path to picture
        BitmapImage image = new BitmapImage(); //create bitmap image blank
        if (filePath.Contains("Assets")) //if standart picture
        {
            LoadImageFromAssetsLibrary(image, filePath);
            return image;
        }
        else
        {
            LoadImageFromString(image, filePath);
            return image;
        }
    }
    //for this method required access
    private async Task LoadImageFromString(BitmapImage image, string path)
    {
        StorageFolder folder = KnownFolders.PicturesLibrary; //get folder
        StorageFile file = await folder.GetFileAsync(path); //find and read file
        //set source of file to image
        using (IRandomAccessStream stream = await file.OpenAsync(FileAccessMode.Read))
        {
            await image.SetSourceAsync(stream);
        }
    }
    //this work correctly
    private async Task LoadImageFromAssetsLibrary(BitmapImage image, string path)
    {
        StringBuilder builder = new StringBuilder();
        builder.Append("ms-appx:///");
        builder.Append(path);
        string localPath = builder.ToString();

        Uri requestedFileUri = new Uri(localPath); //set default folder
        StorageFile file = await StorageFile.GetFileFromApplicationUriAsync(requestedFileUri); //read file
        //set source of file to image
        using (IRandomAccessStream stream = await file.OpenAsync(FileAccessMode.Read))
        {
            await image.SetSourceAsync(stream);
        }
    }

另外,我允许访问pic文件夹:

enter image description here


EDIT3

enter image description here

1 个答案:

答案 0 :(得分:1)

您可以使用或不使用用户权限访问不同的地方(这就是您要求的)。首先,我会给出解释,然后我会给出答案。如果您愿意,请跳至答案部分。

无用户权限可访问的位置


  • 安装文件夹
  • 漫游数据文件夹
  • 本地数据文件夹
  • [设置](从技术上讲,您只需编写值,但仍值得列出)

  • 漫游数据文件夹
  • 本地数据文件夹
  • [设置]


在您的App Manifest(功能)中声明时可访问的位置


读/写

Known Folders

  • 音乐库
  • 文件库
  • 图片库
  • 视频库
  • 可移动存储

您必须直接要求用户为您选择所有其他文件。您可以使用FileOpenPickerFolderPicker类执行此操作。然后,您可以将这些对象存储在FutureAccessList中,以便将来使用。



答案


如果

  • 相关文件夹位于Pictures Library(如果您或用户已在D:\Pictures\...的情况下手动将其包含在库中),

  • 您已在App Manifest的{​​{1}}中添加了对图片库的访问权限。

然后你确实可以“绑定”那些文件。

'绑定'文件

创建Capabilities。此转换器将接受路径字符串,解析它以查找图片库中的文件名和位置,并使用IValueConverter访问图片库。

这是一个KnownFolders.PicturesLibrary进程。转换器不能是异步的,所以基本过程如下:

在转换器

  • 解析图像,确保图像正确无误。
  • 创建一个空白async对象。
  • 将字符串和BitmapImage传递给异步BitmapImage方法

LoadImageFromString方法

  • LoadImageFromString
  • 中检索有问题的StorageFolder
  • 找到该文件。
  • 可选:检索文件缩略图。
  • 可选:将传递的KnownFolders.PicturesLibrary参数的Source(使用BitmapImage.SetSource)设置为缩略图。
  • 读入文件(BitmapImage)。
  • await参数的Source(使用BitmapImage.SetSource)设置为文件内容,必要时使用BitmapImage对其进行解码。

现在,您将异步加载来自ViewModel的数据(应该解析您的JSON),找到有问题的数据,并将BitmapDecoder控件的源设置为其内容。



最后一点

如果这不是专为用户设计的应用,并且您的所有图片都在该文件夹中,您也可以让您的应用手动存储该文件夹的访问点并从中检索所有图像。这显然不是针对消费者驱动的应用程序的建议方法,但可以完成。

编辑:鉴于上面的例子,这是你缺少的。从这个示例中获取文件读取可能需要一些额外的工作(使用上面提到的Image),但也可能没有。

BitmapDecoder