title: WPF Change method assigned to button click temporarily
body: <p>I'm trying to change the button onclick handler / method assigned to button for a short time period.</p>
  
  <p>In other words... user clicks button -> primary task of button executes -> if user clicks button again within... say 3 seconds -> secondary task of button executes.</p>
  
  <p>If user does not click the button in 3 seconds, the primary task is restored to the button.</p>
  
  <p>I've succeeded in changing and restoring the button functionality... but the secondary method is not being executed completely.</p>
  
  <p>Here's the xaml and cs code... I've added comments in the cs code so it'd be easy to figure out what I'm trying to do, and where I am facing issues.</p>
  
  <p>MainWindow.xaml:</p>
  
  <pre><code>&lt;Window x:Class="UITest.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:UITest"
          mc:Ignorable="d"
          Title="MainWindow" Height="519" Width="656"&gt;
      &lt;StackPanel&gt;
          &lt;Button x:Name="button1" Width="60" Height="30" Content="button" Margin="10 10 0 0" BorderThickness="0" BorderBrush="{x:Null}" Padding="0" HorizontalAlignment="Left" VerticalAlignment="Top" Background="Bisque" FontSize="16"&gt;
              &lt;Button.Style&gt;
                  &lt;Style TargetType="Button"&gt;
                      &lt;Setter Property="Template"&gt;
                          &lt;Setter.Value&gt;
                              &lt;ControlTemplate TargetType="Button"&gt;
                                  &lt;StackPanel Background="{TemplateBinding Background}"&gt;
                                      &lt;ContentPresenter /&gt;
                                  &lt;/StackPanel&gt;
                              &lt;/ControlTemplate&gt;
                          &lt;/Setter.Value&gt;
                      &lt;/Setter&gt;
                  &lt;/Style&gt;
              &lt;/Button.Style&gt;
          &lt;/Button&gt;
  
          &lt;Label x:Name="label1" Width="200" Height="30" Margin="10 10 0 0" BorderThickness="0" BorderBrush="{x:Null}" Padding="0" HorizontalAlignment="Left" VerticalAlignment="Top" FontSize="20" Content="label"&gt;
          &lt;/Label&gt;
      &lt;/StackPanel&gt;
  &lt;/Window&gt;
  </code></pre>
  
  <p>MainWindow.xaml.cs</p>
  
  <pre><code>namespace UITest
  {
      public partial class MainWindow : Window
      {
          bool isClick2Done = true;
          public MainWindow()
          {
              InitializeComponent();
              this.button1.Click += Button1_Click1;
          }
  
          //primary function of button
          private async void Button1_Click1(object sender, RoutedEventArgs e)
          {
              label1.Content = "primary";
  
              //wait for a second, to avoid human error of double click
              await Task.Delay(1000);
  
              changeButtonFunction();
          }
  
          //secondary function of button
          private async void Button1_Click2(object sender, RoutedEventArgs e)
          {
              isClick2Done = false;   //click2 isn't done yet
              label1.Content = "secondary";
  
              //delay function
              //to observe whether this secondary method gets completed or not
              await Task.Delay(3000);
              label1.Content = "secondary after wait";
              await Task.Delay(2000);
              isClick2Done = true;   //click2 is now done
              restoreButtonFunction();
          }
  
          private async void changeButtonFunction()
          {
              //set new function for button
              this.button1.Click -= Button1_Click1;
              this.button1.Click += Button1_Click2;
  
              //button is now green - indicator that button has new function
              button1.Background = Brushes.Green;
  
              //keep new function for specific seconds
              //is there a better way of doing this?
              await Task.Delay(3000);
  
              //restore original button function
              while(!isClick2Done) { }
              restoreButtonFunction();
          }
  
          private async void restoreButtonFunction()
          {
              button1.Background = Brushes.Bisque;
              label1.Content = "label";
              this.button1.Click -= Button1_Click2;
              this.button1.Click += Button1_Click1;
          }
      }
  }
  </code></pre>
  
  <p>EDIT: I think the problem is - restoreButtonFuntion() gets completed before Button1_Click2() does... I'm not sure though.</p>