2015-10-29 5 views
0

Pouvez-vous s'il vous plaît quelqu'un me montrer un exemple sur le web ou expliquer la mise à jour de l'image dans WPF MVVM C#.WPF MVVM C# Mise à jour de l'image

Mon code XAML:

<Image Source="{Binding PicturePath}" VerticalAlignment="Center" Margin="0,0,10,0"/> 

code C#

private string _picturepath; 
public string PicturePath 
{ 
    get { return _picturepath; } 
    set 
    { 
     _picturepath = value; 
     NotifyPropertyChanged("PicturePath"); 
    } 
} 

PicturePath = IconPath + @"\Logo.png"; 

Et quand le changement d'image, mettre à jour PicturePath, mais l'image dans le programme restent les mêmes. De quoi ai-je besoin de plus?

+1

Probablement, vous devez implémenter INotifyPropertyChanged pour notifier la vue à propos des modifications. Quel modèle MVVM utilisez-vous? – marcinax

+0

Avez-vous implémenté INotifyPropertyChanged? – Lennart

+0

NotifyPropertyChanged vous pensez? Oui je l'ai .. ou tu penses autre chose? – esispaned

Répondre

1

Voici ce que je me suis retrouvé dans mon projet (et je dois dire qu'il a fallu un certain temps de tester différentes choses qui semblaient presque le travail). Vous pouvez voir le code commenté qui ne fonctionnait pas 100% ne me souviens pas pourquoi)

Donc, toutes mes images de l'actif de l'application qui commencent par "ms-appx:" J'utilise avec le réglage de la source sans charger le flux , parce que ceux-ci ne changent jamais (images par défaut, etc)

Les autres images qui ont été créées ou modifiées par l'utilisateur, j'ai dû recharger et définir la source avec le résultat de la lecture du fichier (sinon, quand ils ont été changés parfois ils ne l'étaient pas mise à jour)

Donc, fondamentalement, j'utilise ce convertisseur sur presque tous les endroits où j'utilise des images qui peuvent changer (sans changer leur nom).

définissent votre convertisseur: (. Une autre solution consiste à nommer différemment et vos images lorsque vous mettez à jour le chemin source, il fonctionne très bien)

<converters:ImageConverter x:Key="ImageConverter" /> 

Et puis utiliser comme cette

<Image Source="{Binding PictureFilename, Converter={StaticResource ImageConverter}}" 
     HorizontalAlignment="Center" 
     VerticalAlignment="Center"/> 

public class ImageConverter : IValueConverter 
{ 
    public object Convert(object value, Type targetType, object parameter, string language) 
    { 
     try 
     { 
      var CapturedImage = new BitmapImage(); 
      CapturedImage.CreateOptions = BitmapCreateOptions.IgnoreImageCache; 
      if (((string)value).StartsWith("ms-appx:")) 
      { 
       CapturedImage.UriSource = new Uri((string)value, UriKind.RelativeOrAbsolute); 
       return CapturedImage; 

      } 
      var file = (StorageFile.GetFileFromPathAsync(new Uri((string)value, UriKind.RelativeOrAbsolute).LocalPath).AsTask().Result); 
      using (IRandomAccessStream fileStream = file.OpenAsync(FileAccessMode.Read).AsTask().Result) 
      { 
       CapturedImage.SetSource(fileStream); 
       return CapturedImage; 

      } 
     } 
     catch (Exception e) 
     { 
      Logger.Error("Exception in the image converter!", e); 
      return new BitmapImage(); 
     } 

     //BitmapImage img = null; 
     //if (value is string) 
     //{ 
     // img = new BitmapImage(); 
     // img.CreateOptions = BitmapCreateOptions.IgnoreImageCache; 
     // img.UriSource = new Uri((string)value, UriKind.RelativeOrAbsolute); 
     //} 

     //if (value is Uri) 
     //{ 
     // img = new BitmapImage(); 
     // img.CreateOptions = BitmapCreateOptions.IgnoreImageCache; 
     // img = new BitmapImage((Uri)value); 
     //} 

     //return img; 
    } 

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

Vous devez implémenter l'interface INotifyPropertyChanged, ajouter ce code, puis appeler OnPropertyChanged() à partir du setter de PicturePath.

void OnPropertyChanged([CallerMemberName] string propertyName = "") 
{ 
    PropertyChangedEventHandler handler = PropertyChanged; 
    if (handler != null) 
    { 
     handler(this, new PropertyChangedEventArgs(propertyName)); 
    } 
} 
+0

OP a déjà fait cela. – Clemens

+0

pas avant que je posté. –

+0

OP parle d'écraser l'image sur le disque. Dans ce cas, l'implémentation d'INPC sur une chaîne sur le chemin ne déclenchera pas ce qu'il demande. –

0

Alors maintenant j'ai fait seul procjet seulement pour la liaison d'image

Code ImageConverter:

public class ImageConverter : IValueConverter 
{ 
    public object Convert(object value, Type targetType, object parameter, CultureInfo language) 
    { 
     try 
     { 
      return new BitmapImage(new Uri((string)value)); 
     } 
     catch 
     { 
      return new BitmapImage(); 
     } 
    } 

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

MainWindowViewModel:

public class MainWindowViewModel : ViewModelBase 
{ 
    public MainWindowViewModel() 
    { 
     Changetopicone = new RelayCommand(param => piconevoid()); 
     Changetopictwo = new RelayCommand(param => pictwovoid()); 
     LogoSourcePath = Path.GetDirectoryName(System.Reflection.Assembly.GetEntryAssembly().Location); 
    } 

    private void piconevoid() 
    { 
     PicturePath = LogoSourcePath + @"\pic1.png"; 
    } 

    private void pictwovoid() 
    { 
     PicturePath = LogoSourcePath + @"\pic2.png"; 
    } 

    public string LogoSourcePath { get; set; } 

    private string _picturepath; 
    public string PicturePath 
    { 
     get { return _picturepath; } 
     set 
     { 
      _picturepath = value; 
      NotifyPropertyChanged("PicturePath"); 
     } 
    } 

    public ICommand Changetopicone 
    { 
     get; 
     set; 
    } 

    public ICommand Changetopictwo 
    { 
     get; 
     set; 
    } 
} 

MainWindow:

<StackPanel> 
     <Button Command="{Binding Changetopicone}" Content="Changetopicone"/> 
     <Button Command="{Binding Changetopictwo}" Content="Changetopictwo"/> 
     <Image Source="{Binding PicturePath, Converter={StaticResource ImgCon}}" VerticalAlignment="Center" Width="200" Height="200"/> 
    </StackPanel> 

Dans mon programme, j'ai un problème, donc je fait ce projet autonome pour être sûr que travaux.

Merci pour toute l'aide!

+0

S'il vous plaît noter que dans mon cas cela ne fonctionnait pas lorsque les images sont écrasées pendant que l'application fonctionne parfois, donc si vous trouvez quelques problèmes essayez de jouer avec le convertisseur un peu plus (bonne chose est que toute cette logique est maintenant – kirotab

+0

Maintenant, j'ai trouvé un problème dans mon application parce que j'ai "PropertyChanged" sur cette instance, puis je change d'icône et je retourne à la classe "PropertyChanged" ... et je fais ça à l'infini :) – esispaned