C# 在WPF中,如何在一秒钟后更改边框的背景色?

C# 在WPF中,如何在一秒钟后更改边框的背景色?,c#,wpf,C#,Wpf,我点击按钮边框的背景是蓝色的,一秒钟后它应该是红色的。它是红色的,但不是蓝色的。为什么? <Window x:Class="WpfApplication1.Window1" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" Title="Window1" Height="300

我点击按钮边框的背景是蓝色的,一秒钟后它应该是红色的。它是红色的,但不是蓝色的。为什么?

<Window x:Class="WpfApplication1.Window1"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Title="Window1" Height="300" Width="300">
    <Border Width="111" Name="op" Height="111">
        <Button Name="opbtn" Click="opbtn_Click" Width="50" Height="23">click</Button>
    </Border>
</Window>

因为你把UI线程和那个循环绑在一起了。UI线程从来没有机会将您的第一次更改应用到边界笔刷,因为它正忙于在这个紧循环中搅动您的CPU。您应该使用
Dispatchermer
或动画来实现这一点。使用
Dispatchermer
的示例:

private void opbtn_Click(object sender, RoutedEventArgs e)
{
    op.BorderBrush = System.Windows.Media.Brushes.Blue;

    var dispatcherTimer = new DispatcherTimer();
    dispatcherTimer.Interval = TimeSpan.FromSeconds(1);
    dispatcherTimer.Tick += delegate
    {
        op.BorderBrush = System.Windows.Media.Brushes.Red;
        dispatcherTimer.Stop();
    };

    dispatcherTimer.Start();
}

因为你把UI线程和那个循环绑在一起了。UI线程从来没有机会将您的第一次更改应用到边界笔刷,因为它正忙于在这个紧循环中搅动您的CPU。您应该使用
Dispatchermer
或动画来实现这一点。使用
Dispatchermer
的示例:

private void opbtn_Click(object sender, RoutedEventArgs e)
{
    op.BorderBrush = System.Windows.Media.Brushes.Blue;

    var dispatcherTimer = new DispatcherTimer();
    dispatcherTimer.Interval = TimeSpan.FromSeconds(1);
    dispatcherTimer.Tick += delegate
    {
        op.BorderBrush = System.Windows.Media.Brushes.Red;
        dispatcherTimer.Stop();
    };

    dispatcherTimer.Start();
}

WPF在此行之后不会立即刷新布局

op.BorderBrush = System.Windows.Media.Brushes.Blue;
尝试使用
op.UpdateLayout()
强制刷新布局:


WPF在此行之后不会立即刷新布局

op.BorderBrush = System.Windows.Media.Brushes.Blue;
尝试使用
op.UpdateLayout()
强制刷新布局:


首先,200毫秒是五分之一秒,不是1秒

之所以只看到红色,是因为代码完成后,边框是红色的。在循环之前或循环期间,您的代码不会产生控制,因此不会绘制蓝色

如果您想为控件的背景颜色设置动画,如果按照此答案中的示例进行操作,您可能会获得更令人满意的结果


如果你喜欢立即改变颜色,那么你有几种方法可以做到这一点,正如我的同事们详细介绍的那样。如果你想让气味特别刺激,可以使用旧的
系统.Windows.Forms.Application.DoEvents
,我相信这仍然有效

首先,200毫秒是五分之一秒,而不是1秒

之所以只看到红色,是因为代码完成后,边框是红色的。在循环之前或循环期间,您的代码不会产生控制,因此不会绘制蓝色

如果您想为控件的背景颜色设置动画,如果按照此答案中的示例进行操作,您可能会获得更令人满意的结果


如果你喜欢立即改变颜色,那么你有几种方法可以做到这一点,正如我的同事们详细介绍的那样。如果你想让气味特别刺激,可以使用旧的
系统.Windows.Forms.Application.DoEvents
,我相信这仍然有效

既然WPF允许在XAML本身中进行类似的操作,为什么还要编写代码呢。请参见下面的示例

<StackPanel Orientation="Horizontal" Height="24">
    <Border BorderThickness="2">
        <Border.BorderBrush>
            <SolidColorBrush x:Name="BorderBrush" />
        </Border.BorderBrush>
        <Button Content="Click me" Width="64" Height="24">
            <Button.Triggers>
                <EventTrigger RoutedEvent="Button.Click">
                    <BeginStoryboard>
                        <Storyboard>
                            <ColorAnimation To="Red"
                                        Duration="0:0:1" 
                                        Storyboard.TargetName="BorderBrush"
                                        Storyboard.TargetProperty="Color"/>
                        </Storyboard>
                    </BeginStoryboard>
                </EventTrigger>
            </Button.Triggers>
        </Button>
    </Border>
</StackPanel>


您可以根据自己的喜好对其进行修改,使其成为资源的一部分,以便可以重用,等等。所有这些都不需要涉及您的代码

既然WPF允许在XAML本身中进行类似的操作,为什么还要编写代码呢。请参见下面的示例

<StackPanel Orientation="Horizontal" Height="24">
    <Border BorderThickness="2">
        <Border.BorderBrush>
            <SolidColorBrush x:Name="BorderBrush" />
        </Border.BorderBrush>
        <Button Content="Click me" Width="64" Height="24">
            <Button.Triggers>
                <EventTrigger RoutedEvent="Button.Click">
                    <BeginStoryboard>
                        <Storyboard>
                            <ColorAnimation To="Red"
                                        Duration="0:0:1" 
                                        Storyboard.TargetName="BorderBrush"
                                        Storyboard.TargetProperty="Color"/>
                        </Storyboard>
                    </BeginStoryboard>
                </EventTrigger>
            </Button.Triggers>
        </Button>
    </Border>
</StackPanel>


您可以根据自己的喜好对其进行修改,使其成为资源的一部分,以便可以重用,等等。所有这些都不需要涉及您的代码

您是否知道在选择分组中的另一个控件时(尝试实现高亮显示,暂时使用C#路线)要取消着色。很抱歉,回复太晚。尝试使用Style.Triggers。为属性IsFoused和值“true”添加一个触发器。将setter添加到触发器并将背景设置为绿色。无需取消着色,因为当Isfocused变为false时,触发器也将恢复原始背景。您知道在选择分组中的另一个控件时取消着色吗(尝试实现高亮显示,暂时转到C#路线)。抱歉,回复太晚。尝试使用Style.Triggers。为属性IsFoused和值“true”添加一个触发器。将setter添加到触发器并将背景设置为绿色。当Isfocused变为false时,触发器也将恢复原始背景,因此无需取消颜色。