10

我有两个Windows申请。其中一个MainWindow用于设置,另一个用于设置。通过使用并将其设置为SettingsWindow单击设置按钮时打开。ShowDialogOwnerMainWindow

我在SettingsWindow窗口的最底部有一个按钮,它在 is 时将颜色更改红色,对于. 但是当光标在 MainWindow 上时它不会改变。下图是为了清楚。我该如何解决这个问题?IsMouseOverTrueFalse

案例:光标不在设置窗口,但它保持红色,没有变化。

在此处输入图像描述

Xml代码:

<Window x:Class="AltoSS.SettingsWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="SettingsWindow"
        Height="150"
        Width="360"
        WindowStyle="None"
        AllowsTransparency="True"
        WindowStartupLocation="CenterOwner">

  <!-- Other control codes-->
  <Button Grid.Row="2" Content="KAYDET" 
          FontSize="15"
          FontWeight="Bold"
          BorderBrush="Gray"
          BorderThickness="0,2,0,2">
    <Button.Style>
      <Style TargetType="Button">
        <Setter Property="Background" Value="Blue"/>
        <Setter Property="Template">
          <Setter.Value>
            <ControlTemplate TargetType="Button">
              <Border Background="{TemplateBinding Background}">
                <ContentPresenter HorizontalAlignment="Center" VerticalAlignment="Center"/>
              </Border>
              <ControlTemplate.Triggers>
                <Trigger Property="IsMouseOver" Value="True">
                  <Setter Property="Background" Value="Red"/>
                  <Setter Property="Foreground" Value="White"/>
                </Trigger>
              </ControlTemplate.Triggers>
            </ControlTemplate>
          </Setter.Value>
        </Setter>
      </Style>
    </Button.Style>
  </Button>
</Window>
4

3 回答 3

3

好吧,经过一番研究,我找不到任何合乎逻辑的原因。对我来说,这更像是一个错误。因此,如果有人确切知道为什么会发生这种情况,请告诉我们!

无论如何,我想出了一个解决方法。基本上,我们可以使用 Show() 并添加一些代码来更接近模态行为 - 例如禁用父窗口,直到对话框关闭或用户选择了确定或取消。

例子:

SettingsWindow settingsWindow = new SettingsWindow(); 
this.IsEnabled = false; //disables the main window 
settingsWindow.Owner = this; // main window is the settings window owner 
settingsWindow.Show(); 
settingsWindow.Closed += (o, e1) => { onWindowClosed(o,e1); }; // this is the close event

订阅 settingsWindow 关闭事件后,我们现在可以在 settingsWindow 关闭时再次启用父窗口:

private void onWindowClosed(object sender, EventArgs e)
{
    this.IsEnabled = true;
}

触发器现在可以正常工作,并且父窗口被禁用,直到其子窗口关闭。

于 2016-09-01T16:18:15.433 回答
1

我认为您必须手动观察鼠标位置。为此,您可以使用 Peheje在此处发布的代码。

我用它来编写一个工作示例。离开窗口时,Button 会获得正确的样式。

using System.Runtime.InteropServices;
using Point = System.Drawing.Point;

[DllImport("user32.dll")]
[return: MarshalAs(UnmanagedType.Bool)]
static extern bool GetCursorPos(ref Point lpPoint);

public bool IsMouseOverButton {
    get { return _isMouseOverButton; }
    set {
        if (value == _isMouseOverButton) return;
        _isMouseOverButton = value;
        OnPropertyChanged();
    }
}

public SettingsWindow()
{
    InitializeComponent();

    new Thread(() =>
    {
        while (true)
        {
            //Logic
            Point p = new Point();
            GetCursorPos(ref p);

            //Update UI
            Application.Current.Dispatcher.Invoke(() =>
            {
                double btnLeft = DlgWindow.Left;
                double btnRight = btnLeft + DlgBtn.ActualWidth;
                double btnBottom = DlgWindow.Top + DlgWindow.ActualHeight;
                double btnTop = btnBottom - DlgBtn.ActualHeight;

                IsMouseOverButton =
                    p.X >= btnLeft && p.X <= btnRight &&
                    p.Y >= btnTop && p.Y <= btnBottom;
            });

            //async wait (non blocking)
            (new ManualResetEvent(false)).WaitOne(100);
        }
    }).Start();
}

xml

<Window x:Name="DlgWindow"
        DataContext="{Binding RelativeSource={RelativeSource Self}}" 
        AllowsTransparency="True">

  <Button x:Name="DlgBtn"
          Height="50"
          VerticalAlignment="Bottom"
          BorderBrush="Gray"
          BorderThickness="0,2,0,2"
          Content="KAYDET"
          FontSize="15"
          FontWeight="Bold">
    <Button.Style>
      <Style TargetType="Button">
        <Setter Property="Background" Value="Blue"/>
        <Setter Property="Template">
          <Setter.Value>
            <ControlTemplate TargetType="Button">
              <Border Background="{TemplateBinding Background}">
                <ContentPresenter HorizontalAlignment="Center" VerticalAlignment="Center"/>
              </Border>
            <ControlTemplate.Triggers>
              <DataTrigger Binding="{Binding IsMouseOverButton}" Value="True">
                <Setter Property="Background" Value="Red" />
                <Setter Property="Foreground" Value="White" />
              </DataTrigger>
            </ControlTemplate.Triggers>
          </ControlTemplate>
        </Setter.Value>
      </Setter>
    </Style>
  </Button.Style>
</Button>
于 2016-09-26T06:16:48.187 回答
0

这对我有用:在设置 Window.Resources 下定义样式资源(用于按钮) - 然后此样式设置新模板(边框),默认背景为蓝色,并且 IsMouseOver 触发器将其更改为红色。显式地隐式引用样式(两者都对我有用)。

小测试项目链接:https ://1drv.ms/u/s!AhlMAmchX3R6nDJ1MXS6DxlRXtnA

<Window x:Class="IsMouseOverTriggerSecondWindow.SettingsWindow"
        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:IsMouseOverTriggerSecondWindow"
        mc:Ignorable="d"
        Title="SettingsWindow" Height="170" Width="330">

    <!-- my settings window button style-->
    <!-- defined as a resource in SettingsWindow.xaml, so it doesnt effect MainWindow -->
    <Window.Resources>
        <Style TargetType="Button" >
            <Setter Property="Background" Value="Blue"/>
            <Setter Property="Template">
                <Setter.Value>
                    <ControlTemplate TargetType="Button">
                        <Border Background="{TemplateBinding Background}">
                            <ContentPresenter Content="{TemplateBinding Content}" 
                                              HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}" 
                                              VerticalAlignment="{TemplateBinding VerticalContentAlignment}" />
                        </Border>
                    </ControlTemplate>
                </Setter.Value>
            </Setter>
            <Style.Triggers>
                <Trigger Property="IsMouseOver" Value="True">
                    <Setter Property="Background" Value="Red" />
                </Trigger>
            </Style.Triggers>
        </Style>
    </Window.Resources>

    <Grid>
        <TextBlock Text="This is the settings window" />
        <Button Content="KAYDET" Height="30" VerticalAlignment="Bottom" Foreground="White" FontWeight="Bold" />
    </Grid>
</Window>
于 2016-09-20T09:50:57.380 回答