Во-первых, StartAsync
не хватает операторов ожидания, и он будет работать синхронно.
public async Task StartAsync(CancellationToken token)
{
ApplicationToken = token;
while (true)
{
if (ApplicationToken.IsCancellationRequested) break;
await Task.Delay(10, ApplicationToken); // => you may change it to concrete task
}
}
Во-вторых, класс CancellationToken
в Foo
является избыточным, вы даже не инициализируете его.
new Bot().StartAsync(tokenSource.Token);
внутри метода Start не ожидается, поэтому выполнение текущего метода продолжается до завершения вызова.
И поскольку метод Start
является недействительным, вы должны использовать метод GetAwaiter()
, чтобы выполнить задачу в классе Bot
.
public void Start()
{
try
{
new Bot().StartAsync(tokenSource.Token).GetAwaiter();
}
catch (Exception ex)
{
Console.WriteLine(ex.ToString());
}
}
Наконец, если метод StopTask_Click
является членом класса Foo
, он должен нормально работать.
Это пример того, как отменить задачу, используя CancellationTokenSource
public partial class Form1 : Form
{
private readonly Foo foo = new Foo();
private void button1_Click(object sender, EventArgs e)
{
foo.Start();
}
private void button2_Click(object sender, EventArgs e)
{
foo.Cancel();
}
}
public class Foo
{
private readonly CancellationTokenSource tokenSource = new CancellationTokenSource();
public void Start()
{
try
{
new Bot().StartAsync(tokenSource.Token).GetAwaiter();
}
catch (Exception ex)
{
Console.WriteLine(ex.ToString());
}
}
public void Cancel()
{
tokenSource.Cancel();
}
}
public class Bot
{
private CancellationToken ApplicationToken;
public async Task StartAsync(CancellationToken token)
{
ApplicationToken = token;
while (true)
{
if (ApplicationToken.IsCancellationRequested) break;
await Task.Delay(10, ApplicationToken);
}
}
}