Привязать IsMouseOver к ViewModel внутри UserControl - PullRequest
0 голосов
/ 19 мая 2018

Я создаю пользовательский элемент управления меню, который изменяет изображения (файлы .PNG) при выборе или наведении курсора на MVVM.Прямо сейчас изображение меняется, когда я выбираю пункт меню, но я изо всех сил пытаюсь заставить партию работать.Вот код, где я назначаю ViewModel для View:

<DataTemplate DataType="{x:Type viewModel:MyMenuItem}">
    <view:MyMenuItemControl/>
</DataTemplate>

А вот код, который у меня есть для моего UserControl:

<Grid>
    <Image Source="{Binding DisplayImage}">
        <Image.InputBindings>
            <MouseBinding Gesture="LeftClick" Command="{Binding LeftClickCommand}"/>
        </Image.InputBindings>
        <Image.Style>
            <Style TargetType="{x:Type Image}">
                <Style.Triggers>
                    <Trigger Property="IsMouseOver" Value="True">
                        <Setter Property="IsMouseOver" Value="{Binding Path=IsHovered, Mode=OneWayToSource}"/>
                    </Trigger>
                </Style.Triggers>
            </Style>
        </Image.Style>
    </Image>
</Grid>

Это не компилируется из-за IsMouseOverсвойство доступно только для чтения, но я не могу понять, как обновить ViewModel, когда происходит этот триггер.Я довольно новичок в WPF и MVVM, поэтому прошу прощения, если это немного невежественно.Я искал около 2 часов и не смог найти ответ, который мог бы понять и продвинуться вперед.

Редактировать: вот вариант 2, который, похоже, тоже не работает.Это компилирует, но не обновляет изображение при наведении мыши на элемент:

<Grid>
    <Image Source="{Binding DisplayImage}">
        <Image.InputBindings>
            <MouseBinding Gesture="LeftClick"  Command="{Binding LeftClickCommand}"/>
        </Image.InputBindings>
        <Image.Style>
            <Style TargetType="{x:Type Image}">
                <Style.Triggers>
                    <Trigger Property="IsMouseOver" Value="True">
                        <Setter Property="Source" Value="{Binding DisplayHoverImage}"/>
                    </Trigger>
                </Style.Triggers>
            </Style>
        </Image.Style>
    </Image>
</Grid>

Решение, с которым я собираюсь:

<Grid>
    <Image>
        <Image.InputBindings>
            <MouseBinding Gesture="LeftClick"  Command="{Binding LeftClickCommand}"/>
        </Image.InputBindings>
        <Image.Style>
            <Style TargetType="{x:Type Image}">
                <Setter Property="Source" Value="{Binding DisplayImage}"/>
                <Style.Triggers>
                    <Trigger Property="IsMouseOver" Value="True">
                        <Setter Property="Source" Value="{Binding DisplayHoverImage}"/>
                    </Trigger>
                </Style.Triggers>
            </Style>
        </Image.Style>
    </Image>
</Grid>

1 Ответ

0 голосов
/ 15 марта 2019

Сначала определите новый элемент управления, полученный из элемента управления, который вы пытаетесь использовать:

public class HoverOverImage : Image
{
    public static DependencyProperty MouseOverFrameAreaProperty = DependencyProperty.Register("MouseOverFrameArea", typeof(bool), typeof(HoverOverImage)
        , new FrameworkPropertyMetadata(false, OnMouseOverFrameAreaChanged));
    private bool _mouseOverFrameArea = false;

    public bool MouseOverFrameArea
    {
        get => _mouseOverFrameArea;
        set
        {
            _mouseOverFrameArea = value;
            if (DataContext != null && DataContext.GetType()==typeof(MyViewModel))
                ((MyViewModel)DataContext).MouseOverFrameArea = value;
        }
    }
    private static void OnMouseOverFrameAreaChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
    {
        ((HoverOverImage)d).MouseOverFrameArea = (bool)e.NewValue;
    }
}

Затем в XAML вы должны добавить:

<local:HoverOverImage x:Name="framesourceImage" RenderOptions.BitmapScalingMode="NearestNeighbor" Source="{Binding CurrentFrame}">
                    <local:HoverOverImage.Style>
                        <Style TargetType="{x:Type local:HoverOverImage}">
                            <Style.Triggers>
                                <Trigger Property="IsMouseOver" Value="True">
                                    <Setter Property="MouseOverFrameArea" Value="True"/>
                                </Trigger>
                                <Trigger Property="IsMouseOver" Value="False">
                                    <Setter Property="MouseOverFrameArea" Value="False"/>
                                </Trigger>
                            </Style.Triggers>
                        </Style>
                    </local:HoverOverImage.Style>

...