我如何实现时间延迟?
How do i implement a time delay?
我现在已经进行了 3 周的编程,所以我尝试构建一个记忆游戏。
除了延迟,一切正常。我尝试了很多不同的选择,但不知何故延迟是在 Button_Click
事件结束时。
如果我点击第一个按钮,它会改变内容,但是当我点击第二个按钮时
按钮,无论触发哪个 if
语句,第二张卡片都不会显示。代码在事件结束之前工作正常,然后发生 3 秒的延迟
我想实现的是你可以在短时间内看到第二张卡片
在两张牌都翻过来或消失之前。
P.S。 - 如果我在 "delay" 之后添加 MessageBox
似乎可以工作
但这不是目标,所以是否有类似等待同步或我错过的东西?
代码:
private void Button_Click(object sender, RoutedEventArgs e)
{
var button = (Button)sender;
int index = ContainderGrid.Children.IndexOf(button);
mCounterSecondPic++;
button.Content = new BitmapImage(new Uri(mImgPath[mPairs[index]]));//change content
mPic[mCounterSecondPic-1] = mPairs[index];
button.IsEnabled = false;
if (mPic[0] == mPic[1] & mCounterSecondPic == 2)
{
mCounterSecondPic = 0;
new System.Threading.ManualResetEvent(false).WaitOne(3000); //wait for 3sec
ContainderGrid.Children.RemoveAt(mPairs.IndexOf(mPic[0]));
mPairs.RemoveAt(mPairs.IndexOf(mPic[0]));
ContainderGrid.Children.RemoveAt(mPairs.IndexOf(mPic[0]));
mPairs.RemoveAt(mPairs.IndexOf(mPic[0]));
}
if (mCounterSecondPic == 2 & mPic[0] != mPic[1])
{
mCounterSecondPic = 0;
new System.Threading.ManualResetEvent(false).WaitOne(3000);//wait for3 sec
ContainderGrid.Children.Cast<Button>().ToList().ForEach(resetbuttons =>
{
resetbuttons.IsEnabled = true;
resetbuttons.Content = new BitmapImage(new Uri(mCardBack));
});
}
ps:如果我在 "delay" 之前添加一个消息框,它似乎可以工作
但这不是问题,所以有没有类似等待同步或我错过的东西?
MessageBox.Show("x");
new System.Threading.ManualResetEvent(false).WaitOne(3000);
让我们简化代码:
private void Button_Click(object sender, RoutedEventArgs e)
{
button.Content = "START" //change content
new System.Threading.ManualResetEvent(false).WaitOne(3000); //wait for 3sec
button.Content = "FINISH" //change content
}
这样你就有了以下时间表:
- 你设置内容(但不要see/feel它)
- 您开始等待 3 秒
- 你结束等待 3 秒
- 你设置内容(但不要see/feel它)
- 您退出
Button_Click
方法
- 你居然see/feel内容变了
如您所见,内容更改(在 item1 和 item4)并没有立即发生,而是在很久以后;这是因为 UI 线程在 Button_Click
方法的执行中被阻塞,因此无法刷新图形。
为了实现你想要的,你有两个选择:
- 使用
async/await
:
private async void Button_Click(object sender, RoutedEventArgs e)
{
button.Content = "START" //change content
await Task.Delay(3000); //wait for 3sec asynchronously
button.Content = "FINISH" //change content
}
- 使用
Dispatcher
:
private void Button_Click(object sender, RoutedEventArgs e)
{
new Thread(() =>
{
Dispatcher.Invoke(() => button.Content = "START");
System.Threading.Thread.Sleep(3000);
Dispatcher.Invoke(() => button.Content = "FINISH");
}).Start();
}
我现在已经进行了 3 周的编程,所以我尝试构建一个记忆游戏。
除了延迟,一切正常。我尝试了很多不同的选择,但不知何故延迟是在 Button_Click
事件结束时。
如果我点击第一个按钮,它会改变内容,但是当我点击第二个按钮时
按钮,无论触发哪个 if
语句,第二张卡片都不会显示。代码在事件结束之前工作正常,然后发生 3 秒的延迟
我想实现的是你可以在短时间内看到第二张卡片 在两张牌都翻过来或消失之前。
P.S。 - 如果我在 "delay" 之后添加 MessageBox
似乎可以工作
但这不是目标,所以是否有类似等待同步或我错过的东西?
代码:
private void Button_Click(object sender, RoutedEventArgs e)
{
var button = (Button)sender;
int index = ContainderGrid.Children.IndexOf(button);
mCounterSecondPic++;
button.Content = new BitmapImage(new Uri(mImgPath[mPairs[index]]));//change content
mPic[mCounterSecondPic-1] = mPairs[index];
button.IsEnabled = false;
if (mPic[0] == mPic[1] & mCounterSecondPic == 2)
{
mCounterSecondPic = 0;
new System.Threading.ManualResetEvent(false).WaitOne(3000); //wait for 3sec
ContainderGrid.Children.RemoveAt(mPairs.IndexOf(mPic[0]));
mPairs.RemoveAt(mPairs.IndexOf(mPic[0]));
ContainderGrid.Children.RemoveAt(mPairs.IndexOf(mPic[0]));
mPairs.RemoveAt(mPairs.IndexOf(mPic[0]));
}
if (mCounterSecondPic == 2 & mPic[0] != mPic[1])
{
mCounterSecondPic = 0;
new System.Threading.ManualResetEvent(false).WaitOne(3000);//wait for3 sec
ContainderGrid.Children.Cast<Button>().ToList().ForEach(resetbuttons =>
{
resetbuttons.IsEnabled = true;
resetbuttons.Content = new BitmapImage(new Uri(mCardBack));
});
}
ps:如果我在 "delay" 之前添加一个消息框,它似乎可以工作 但这不是问题,所以有没有类似等待同步或我错过的东西?
MessageBox.Show("x");
new System.Threading.ManualResetEvent(false).WaitOne(3000);
让我们简化代码:
private void Button_Click(object sender, RoutedEventArgs e)
{
button.Content = "START" //change content
new System.Threading.ManualResetEvent(false).WaitOne(3000); //wait for 3sec
button.Content = "FINISH" //change content
}
这样你就有了以下时间表:
- 你设置内容(但不要see/feel它)
- 您开始等待 3 秒
- 你结束等待 3 秒
- 你设置内容(但不要see/feel它)
- 您退出
Button_Click
方法 - 你居然see/feel内容变了
如您所见,内容更改(在 item1 和 item4)并没有立即发生,而是在很久以后;这是因为 UI 线程在 Button_Click
方法的执行中被阻塞,因此无法刷新图形。
为了实现你想要的,你有两个选择:
- 使用
async/await
:
private async void Button_Click(object sender, RoutedEventArgs e)
{
button.Content = "START" //change content
await Task.Delay(3000); //wait for 3sec asynchronously
button.Content = "FINISH" //change content
}
- 使用
Dispatcher
:
private void Button_Click(object sender, RoutedEventArgs e)
{
new Thread(() =>
{
Dispatcher.Invoke(() => button.Content = "START");
System.Threading.Thread.Sleep(3000);
Dispatcher.Invoke(() => button.Content = "FINISH");
}).Start();
}