1

I would like to update the source of Image when MouseMove event is triggered:

<DataTemplate>
...
 <Viewbox  MaxWidth="100" MaxHeight="100" >
  <Image x:Name="Vignette0" Source="{Binding Vignette}" MouseMove="Vignette0_OnMouseMove"/>
 </Viewbox>
</DataTemplate>

[2]
<Image.Style>
 <Style TargetType="Image">
  <Style.Triggers>
   <DataTrigger Binding="{Binding xxxx}" Value="true">
    <Setter Property="Source" Value="{Binding Vignette}" />
   </DataTrigger>
  </Style.Triggers>
 </Style>
</Image.Style>

where Vignette is a property with notification change.

  • I tried [2] to figure something with style.triggers (Change image using trigger WPF MVVM) but in my case the source is dynamic binding (datatemplate)
  • I couldn't put MouseMove in the Binding at xxxx
  • I also tried to do something with the code-behind but I can't figure it out.

Does someone has an idea ?

Raw XAML code:

<DataGrid x:Name="DgTest" ItemsSource="{Binding Evm.RawImagesCollectionView}" AutoGenerateColumns="false"
                      SelectedItem="{Binding Evm.SelectedImage}">
                <DataGrid.GroupStyle>
                    <GroupStyle>
                        <GroupStyle.HeaderTemplate>
                            <DataTemplate>
                                <StackPanel>
                                    <TextBlock Text="{Binding Path=ParentDir}" />
                                </StackPanel>
                            </DataTemplate>
                        </GroupStyle.HeaderTemplate>
                        <GroupStyle.ContainerStyle>
                            <Style TargetType="{x:Type GroupItem}">
                                <Setter Property="Template">
                                    <Setter.Value>
                                        <ControlTemplate TargetType="{x:Type GroupItem}">
                                            <Expander>
                                                <Expander.Header>
                                                    <StackPanel Orientation="Horizontal">
                                                        <TextBlock Text="{Binding Path=ParentDir}" />
                                                        <TextBlock Text="{Binding Path=ItemCount}"/>
                                                        <TextBlock Text=" images"/>
                                                    </StackPanel>
                                                </Expander.Header>
                                                <ItemsPresenter />
                                            </Expander>
                                        </ControlTemplate>
                                    </Setter.Value>
                                </Setter>
                            </Style>
                        </GroupStyle.ContainerStyle>
                    </GroupStyle>
                </DataGrid.GroupStyle>
                <DataGrid.Columns>
                    <DataGridTextColumn Header="Name" Binding="{Binding Name}" IsReadOnly="True"/>
                    <DataGridTextColumn Header="#frames" Binding="{Binding NumberOfFrames}" IsReadOnly="True"/>
                    <DataGridTextColumn Header="#bg" Binding="{Binding NumberOfBackgrounds}" IsReadOnly="True"/>
                    <DataGridTextColumn Header="path" Binding="{Binding ParentDir}" IsReadOnly="True"/>
                    <DataGridTemplateColumn Header="action">
                        <DataGridTemplateColumn.CellTemplate>
                            <DataTemplate>
                                <StackPanel Orientation="vertical" VerticalAlignment="Center">
                                    <StackPanel Orientation="Horizontal">
                                        <Button Content="prepare" Command="{Binding DecodeCommand}" Height="24"/>
                                        <ProgressBar Minimum="0" Maximum="1.00" Value="{Binding PercentDone}" Width="40" Height="24"/>
                                    </StackPanel>
                                    <Viewbox  MaxWidth="100" MaxHeight="100" >
                                        <Image x:Name="VignetteViewBox0" Source="{Binding Vignette}" MouseMove="VignetteViewBox0_OnMouseMove">
                                            <Image.Style>
                                                <Style TargetType="Image">
                                                    <Style.Triggers>
                                                        <DataTrigger Binding="{Binding }" Value="true">
                                                            <Setter Property="Source" Value="{Binding Vignette}" />
                                                        </DataTrigger>
                                                    </Style.Triggers>
                                                </Style>
                                            </Image.Style>
                                        </Image>
                                    </Viewbox>
                                </StackPanel>
                            </DataTemplate>
                        </DataGridTemplateColumn.CellTemplate>
                    </DataGridTemplateColumn>
                </DataGrid.Columns>
            </DataGrid>

the property Vignette:

public BitmapImage Vignette
{
    get
    {
        if (NumberOfFrames > 0)
        {
            var files = Directory.GetFiles(Filedir, "out*");
            if (files.Length >= 5)
                VignetteNumber = VignetteNumber != 5 ? 5 : _rgen.Next(0, files.Length);
            else
                VignetteNumber = _rgen.Next(0, files.Length);
            var filepath = files[VignetteNumber];
            var buffer = new BitmapImage();
            using (Stream imageStreamSource = new FileStream(filepath,
                FileMode.Open, FileAccess.Read, FileShare.Read))
            {
                buffer.BeginInit();
                buffer.CacheOption = BitmapCacheOption.OnLoad;
                buffer.StreamSource = imageStreamSource;
                buffer.EndInit();
            }
            return buffer;
        }
        return null;
    }
}
Community
  • 1
  • 1
Soleil
  • 6,404
  • 5
  • 41
  • 61

1 Answers1

0

Here is a working example of the functionality you trying to achieve. Make sure to change the constant in the view model to refer to the directory where you have some BMP's to test with.
Have a great day :)

MainWindow.xaml

<Window x:Class="WpfApplication13.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:local="clr-namespace:WpfApplication13"
        mc:Ignorable="d"
        Title="MainWindow" Height="350" Width="525" d:DataContext="{d:DesignInstance local:VmMainWindow, IsDesignTimeCreatable=True}">
    <Grid>
        <DataGrid x:Name="dataGrid" ItemsSource="{Binding Items}" AutoGenerateColumns="false">
            <DataGrid.Columns>
                <DataGridTextColumn Header="Name" Binding="{Binding Name}" IsReadOnly="True" Width="150"/>
                <DataGridTemplateColumn Header="BMP" Width="150" IsReadOnly="False">
                    <DataGridTemplateColumn.CellTemplate>
                        <DataTemplate DataType="local:VmItemInGrid">
                            <Viewbox  MaxWidth="100" MaxHeight="100">
                                <Image Source="{Binding BMP}" MouseEnter="Image_MouseEnter" />
                            </Viewbox>
                        </DataTemplate>
                    </DataGridTemplateColumn.CellTemplate>
                </DataGridTemplateColumn>
            </DataGrid.Columns>
        </DataGrid>
    </Grid>
</Window>

MainWindow.xaml.cs (Code-Behind)

using System.Windows;
using System.Windows.Controls;
using System.Windows.Input;

namespace WpfApplication13
{
    /// <summary>
    /// Interaction logic for MainWindow.xaml
    /// </summary>
    public partial class MainWindow : Window
    {
        public MainWindow()
        {
            InitializeComponent();
            DataContext = new VmMainWindow();
        }

        private void Image_MouseEnter(object sender, MouseEventArgs e)
        {
            ((VmItemInGrid)((Image)sender).DataContext).GetNextFile();
        }
    }
}

View-Model parts

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.IO;
using System.Windows.Media.Imaging;

namespace WpfApplication13
{
    public class VmMainWindow : INotifyPropertyChanged
    {
        public event PropertyChangedEventHandler PropertyChanged;

        public List<VmItemInGrid> Items { get; }

        public VmMainWindow()
        {
            Items = new List<VmItemInGrid>
            {
                new VmItemInGrid {Name = "Item1"},
                new VmItemInGrid {Name = "Item2"},
                new VmItemInGrid {Name = "Item3"}
            };
        }
    }

    public class VmItemInGrid : INotifyPropertyChanged
    {
        private const string generalBmpPath = @"C:\Users\Gil\Pictures\TestBMPs\";

        public event PropertyChangedEventHandler PropertyChanged;

        private string filepath;

        public VmItemInGrid()
        {
            GetNextFile();
        }

        public string Name { get; set; }

        public BitmapImage BMP
        {
            get
            {
                var buffer = new BitmapImage();
                using (Stream imageStreamSource = new FileStream(filepath,
                    FileMode.Open, FileAccess.Read, FileShare.Read))
                {
                    buffer.BeginInit();
                    buffer.CacheOption = BitmapCacheOption.OnLoad;
                    buffer.StreamSource = imageStreamSource;
                    buffer.EndInit();
                }
                return buffer;
            }
        }

        public void GetNextFile()
        {
            var allFiles = Directory.GetFiles(generalBmpPath, "*.bmp");
            var random = new Random();
            var index = random.Next(allFiles.Length);
            filepath = allFiles[index];
            PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(nameof(BMP)));
        }
    }
}
G.Y
  • 6,042
  • 2
  • 37
  • 54
  • 1
    Great thanks. The trick to me was to dive in the datacontext, so we can access to the instance that holds the Vignette `((VmItemInGrid)((Image)sender).DataContext).GetNextFile();` Many thanks ! – Soleil Nov 21 '15 at 20:40