简体   繁体   English

如何检索所选图像并将其保存到列表框中或从列表框中保存到独立存储中

[英]how to retrived and save selected image to/from the listbox to/from isolatedstorage

I am retriving images from the media library to list box inside a wrap panel now I want to save the images selected (its a multiple selection listbox) to the isolatedstorage. 我现在要将媒体库中的图像检索到包装面板中的列表框,现在我想将选定的图像(其多个选择列表框)保存到isolatedstorage。

xaml of listbox 列表框的xaml

    <ListBox Name="vaultbox" SelectionMode="Multiple" 
                ItemContainerStyle="{StaticResource ListBoxItemStyle1}">
     <TextBlock Text="It is so lonely here..." Visibility="Collapsed" />
                <ListBox.ItemsPanel>
                    <ItemsPanelTemplate>
                        <toolkit:WrapPanel ItemWidth="200" ItemHeight="200"/>
                    </ItemsPanelTemplate>
                </ListBox.ItemsPanel>
                <ListBox.ItemTemplate>
                    <DataTemplate>
                        <Image Name="image2" 
                               Stretch="Fill" 
                               VerticalAlignment="Top" Source="{Binding}" />
                    </DataTemplate>
                </ListBox.ItemTemplate>
            </ListBox>

I am lost here. 我在这里迷路了。 I was trying to do this. 我正在尝试这样做。

    List<BitmapImage> vltBitmapImage = new List<BitmapImage>();

        foreach (string fileName in fileStorage.GetFileNames("images//*.*"))
        {
            if (fileName == null)
                break;
            string filepath = System.IO.Path.Combine("images", fileName);
            using(IsolatedStorageFileStream imageStream =        
                          fileStorage.OpenFile(filepath,FileMode.Open,FileAccess.Read))
            {
                var imageSource=PictureDecoder.DecodeJpeg(imageStream);
                BitmapImage bitmapImage = new BitmapImage();
                bitmapImage.SetSource(imageStream);
                vltBitmapImage.Add(bitmapImage);
            }
        }


        this.vaultbox.ItemsSource = vltBitmapImage;

using above code i get this exception 使用上面的代码我得到这个异常

'System.Invalid.Operation.Exception Items collection must be empty before using ItemsSource' 'System.Invalid.Operation.Exception在使用ItemsSource之前,Items集合必须为空。

dont know why its the same code almost from what i am showing pictures from media library to the listbox. 不知道为什么我从媒体库向列表框显示图片时几乎都使用相同的代码。

also from a similar list box above but different one i try to save the files to isolatedstorage but i can seem to find out how can i get the image name... see here. 也是从上面的类似列表框中,但从另一个列表框中,我尝试将文件保存到isolatedstorage,但是我似乎可以找出如何获取图像名称...请参阅此处。 Currently am using "name" what can I do for that? 当前正在使用“名称”怎么办?

foreach (BitmapImage item in lstImageFromMediaLibrary.SelectedItems)
{     
    string filepath =System.IO.Path.Combine("images", "name");
    IsolatedStorageFileStream ifs = fileStorage.CreateFile(filepath);
            {
                var bmp = new WriteableBitmap(item);
                bmp.SaveJpeg(ifs,item.PixelWidth,item.PixelHeight,0,90);
            }

        }

I would like to recommend you using MVVM pattern: create the ViewModel and put the collection property inside. 我想建议您使用MVVM模式:创建ViewModel并将collection属性放入其中。 Also, it it very convenient to have the "selected item" property in this ViewModel class and bind the selected item of the ListBox to it. 同样,在此ViewModel类中具有“ selected item”属性并将ListBox的选定项目绑定到它上也非常方便。

It seems it is necessary to introduce the image item representation: it is image with name. 似乎有必要介绍图像项目表示形式:它是带有名称的图像。

public class ImageViewModel : ViewModelBase
{
    public ImageViewModel(string name, string image)
    {
        Name = name;
        Image = image;
    }

    // Name or Path? Please make the choice by yourself! =)
    public string Name { get; private set; }
    public BitmapImage Image { get; private set; }
}

ViewModelBase class (implements INotifyPropertyChanged interface): ViewModelBase类(实现INotifyPropertyChanged接口):

public abstract class ViewModelBase : INotifyPropertyChanged
{
    protected ViewModelBase()
    {
    }

    #region Implementation of INotifyPropertyChanged interface

    public event PropertyChangedEventHandler PropertyChanged;

    protected void RaisePropertyChanged(string propertyName)
    {
        var handler = PropertyChanged;
        if (handler != null)
        {
            var args = new PropertyChangedEventArgs(propertyName);
            handler(this, args);
        }            
    }

    #endregion
}

The main (root) view model. 主(根)视图模型。

public class MainViewModel : ViewModelBase
{
    public MainViewModel()
    {            
        // Call this directly:
        // var images = LoadImages();
        // Images = images;

        // or bind the Command property of Button to the LoadImagesCommand.
        LoadImagesCommand = new RelayCommand((param) => 
            {
                var images = LoadImages();
                Images = new ObservableCollection<ImageViewModel>(images);
            });
    }

    private ObservableCollection<ImageViewModel> _images;
    public ObservableCollection<ImageViewModel> Images
    {
        get { return _images; }
        private set
        {
            if (value == _images)
                return;
            _images = value;
            RaisePropertyChanged("Images");
        }
    }

    private ImageViewModel _selectedImage;
    public ImageViewModel SelectedImage
    {
        get { return _selectedImage; }
        set
        {
            if (value == _selectedImage)
                return;
            _selectedImage = value;
            RaisePropertyChanged("SelectedImage");
        }
    }

    public ICommand LoadImagesCommand { get; private set; }

    private List<ImageViewModel> LoadImages()
    {
        List<ImageViewModel> images = new List<ImageViewModel>();

        // Part of the original code.
        foreach (string fileName in fileStorage.GetFileNames("images//*.*"))
        {
            if (fileName == null)
                break;
            string filepath = System.IO.Path.Combine("images", fileName);
            using (IsolatedStorageFileStream imageStream = fileStorage.OpenFile(filepath,FileMode.Open,FileAccess.Read))
            {
                var imageSource = PictureDecoder.DecodeJpeg(imageStream);
                BitmapImage bitmapImage = new BitmapImage();
                bitmapImage.SetSource(imageStream);

                ImageViewModel imageViewModel = new ImageViewModel(fileName, bitmapImage);
                images.Add(imageViewModel);
            }
        }
    }
}

Window. 窗口。

public class MainView : Window
{
    public MainView()
    {
        InititializeComponent();
        // It is just for simplicity. It would be better to use MVVM Light framework: ViewModel Locator!
        DataContext = new MainViewModel();
    }
}

XAML: XAML:

<!-- Please correct the binding for the Image property inside the ItemStyle -->
<ListBox Name="vaultbox"
         ItemsSource="{Binding Images}"
         SelectedItem={Binding SelectedImage}"
         ItemContainerStyle="{StaticResource ListBoxItemStyle1}"
         Height="493"
         HorizontalAlignment="Left"
         Margin="0,0,0,0"
         VerticalAlignment="Top"
         Width="442"
         SelectionMode="Multiple">
    ...
</ListBox>

Also, please consider asynchronous loading: it won't freeze the UI. 另外,请考虑异步加载:它不会冻结UI。

The exception occures because of this line: 由于此行而发生异常:

  <TextBlock Text="It is so lonely here..." />

You have a child of ListBox. 您有一个ListBox的孩子。 And you try to add more. 您尝试添加更多。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM