Как запустить метод за x секунд?
Я работаю над приложением С# Windows Forms, где мне нужен метод для паузы в течение 30 секунд, пока он не перейдет к следующей строке кода. Я пробовал Thread.Sleep()
, который не подходит для этого приложения, и я понял, что вместо этого я должен использовать какой-то таймер. Я много искал, но не могу понять, как реализовать таймеры.
Мой код ниже, и кто-нибудь может показать мне, как я должен использовать таймер. Я сделал комментарий о том, где я хочу, чтобы метод приостанавливался.
private void start_Vid_Click(object sender, EventArgs e)
{
if (video.State != StateFlags.Running)
{
viewport.Visible = true;
video.Play();
}
//Here I want to wait 30 seconds until the next line of code is triggered
viewport.Visible = false;
viewport2.Visible = true;
pictureBox1.Visible = true;
start_Webc();
video2.Play();
}
Ответы
Ответ 1
Если ваше приложение является .Net 4.5-приложением, то несколько проще использовать Task
:
private async void start_Vid_Click(object sender, EventArgs e)
{
if (video.State != StateFlags.Running)
{
viewport.Visible = true;
video.Play();
}
await Task.Delay(TimeSpan.FromSeconds(30));
viewport.Visible = false;
viewport2.Visible = true;
pictureBox1.Visible = true;
start_Webc();
video2.Play();
}
Ответ 2
Task.Delay недоступен в .NET 4.0, но вы можете запустить задачу, которая будет просто спать в течение 30 секунд, а позже вы можете продолжить работу с потоком пользовательского интерфейса:
Task.Factory.StartNew(() => Thread.Sleep(30 * 1000))
.ContinueWith((t) =>
{
viewport.Visible = false;
viewport2.Visible = true;
pictureBox1.Visible = true;
start_Webc();
video2.Play();
}, TaskScheduler.FromCurrentSynchronizationContext());
Ответ 3
На уровне класса определите экземпляр Timer
(для этого есть несколько классов - для приложения winforms вы должны использовать System.Windows.Forms.Timer
)
static System.Windows.Forms.Timer myTimer = new System.Windows.Forms.Timer();
Затем в вашем методе добавьте строки для обработки своего тика и запустите его:
private void start_Vid_Click(object sender, EventArgs e)
{
if (video.State != StateFlags.Running)
{
viewport.Visible = true;
video.Play();
}
myTimer.Tick += (o,ea) => {
viewport.Visible = false;
viewport2.Visible = true;
pictureBox1.Visible = true;
start_Webc();
video2.Play();
myTimer.Stop();
}
myTimer.Interval = 5000; // 5 seconds
myTimer.Start();
}
Ответ 4
Там также был бы способ с реактивными расширениями:
Observable.Return("Delayed").Delay(TimeSpan.FromSeconds(30)).Subscribe(val => Console.WriteLine("Executing delayed"));
Ответ 5
Мы можем сделать это, используя Task из
System.Threading.Tasks.Task.Factory.StartNew(() =>
{
Thread.Sleep(5000);
this.Invoke(new Action(() =>
Method1()));
});
Ответ 6
System.Threading.Tasks.Task.Delay( 60 * 1000 ).ContinueWith( (_) => StartVoid() );