我有一个C#Windows窗体应用程序,我希望用户能够安排一个定期任务
我的应用程序根据用户界面上输入表单的数据发送电子邮件。用户界面还允许他们将此作为作业“安排”。我真的不想在课外使用,例如Quartz。我也不想使用任务调度程序,因为这需要完全重写我的应用程序。。。我知道这可以通过定时器来完成,并且我已经尝试使用Windows.Forms.Timer,但是,我没有得到想要的结果。我希望它以用户指定的间隔和时间运行,直到设置的结束日期我有一个C#Windows窗体应用程序,我希望用户能够安排一个定期任务,c#,.net,winforms,timer,.net-3.5,C#,.net,Winforms,Timer,.net 3.5,我的应用程序根据用户界面上输入表单的数据发送电子邮件。用户界面还允许他们将此作为作业“安排”。我真的不想在课外使用,例如Quartz。我也不想使用任务调度程序,因为这需要完全重写我的应用程序。。。我知道这可以通过定时器来完成,并且我已经尝试使用Windows.Forms.Timer,但是,我没有得到想要的结果。我希望它以用户指定的间隔和时间运行,直到设置的结束日期 private void Submit_Btn_Click(object sender, EventArgs e) {
private void Submit_Btn_Click(object sender, EventArgs e)
{
bool run = false;
Location_Alert_Timer.Tick += new EventHandler(Location_Alert_Timer_Tick);
if (Schedule_Chk.Checked == true)
{
run = true;
if (Recur_Txt.Text != "" || Recur_Txt.Text != "0")
{
while (run == true)
{
if ((Convert.ToDateTime(DateTime.Now.ToString("MM/dd/yyyy HH:mm")) <= Convert.ToDateTime(End_Date.Value.ToString("MM/dd/yyyy") + " " + Recur_Time_Txt.Text)))
{
//Execute_Command();
DateTime dt1;
DateTime dt2;
TimeSpan ts = new TimeSpan(Convert.ToInt16(Recur_Txt.Text),0,0,0);
//TimeSpan ts = new TimeSpan(0,0,30);
dt1 = Convert.ToDateTime(DateTime.Now.ToString("MM/dd/yyyy HH:mm"));
dt2 = Convert.ToDateTime(DateTime.Now.ToString("MM/dd/yyyy") + " " + Recur_Time_Txt.Text);
if (dt1 >= dt2)
{
Execute_Command();
Location_Alert_Timer.Interval = (Convert.ToDateTime(DateTime.Now.ToString("MM/dd/yyyy") + " " + Recur_Time_Txt.Text + ":00.000").Add(ts) - DateTime.Now).Milliseconds;
Location_Alert_Timer.Start();
while (Convert.ToDateTime(DateTime.Now.ToString("MM/dd/yyyy HH:mm")) <= Convert.ToDateTime(End_Date.Value.ToString("MM/dd/yyyy") + " " + Recur_Time_Txt.Text))
{
Application.DoEvents();
}
}
else
{
Location_Alert_Timer.Interval = (Convert.ToDateTime(DateTime.Now.ToString("MM/dd/yyyy") + " " + Recur_Time_Txt.Text + ":00.000") - DateTime.Now).Milliseconds;
Location_Alert_Timer.Start();
while (exitFlag == false)
{
Application.DoEvents();
}
}
}
else
{
Location_Alert_Timer.Stop();
run = false;
}
}
}
else
{
Execute_Command();
}
}
else
{
Execute_Command();
}
}
void Location_Alert_Timer_Tick(object sender, EventArgs e)
{
if (Convert.ToDateTime(DateTime.Now.ToString("MM/dd/yyyy HH:mm")) <= Convert.ToDateTime(End_Date.Value.ToString("MM/dd/yyyy") + " " + Recur_Time_Txt.Text))
{
Execute_Command();
}
else
{
exitFlag = true;
}
}
private void Submit\u Btn\u单击(对象发送者,事件参数e)
{
bool-run=false;
Location\u Alert\u Timer.Tick+=新事件处理程序(Location\u Alert\u Timer\u Tick);
如果(计划检查==真)
{
run=true;
if(Recur_Txt.Text!=“0”)
{
while(run==true)
{
if((Convert.ToDateTime(DateTime.Now.ToString(“MM/dd/yyyy HH:MM”))=dt2)
{
执行_命令();
Location_Alert_Timer.Interval=(Convert.ToDateTime(DateTime.Now.ToString(“MM/dd/yyyy”)+“”+Recur_Time_Txt.Text+“:00.000”)。添加(ts)-DateTime.Now)。毫秒;
位置\警报\计时器.Start();
while(Convert.ToDateTime(DateTime.Now.ToString(“MM/dd/yyyy HH:MM”))使用类似于此示例的内容怎么样
@kclewis在“提交”按钮单击处理程序中注册勾号事件处理程序,就像您所做的那样,将导致位置\u警报\u计时器\u勾号()第一次单击按钮时调用一次,下一次调用两次,以此类推。它一遍又一遍地注册同一个回调函数,这导致在引发勾号事件时多次调用该回调函数。相反,在初始化时,+=该事件处理程序(可能在构造函数或其他一些setup()函数中)。这样,当计时器滴答声事件引发时,您将得到一个且只有一个对位置\u Alert\u Timer\u Tick()的函数调用。通过社区wiki发布@itsmat您是否假装应用程序永远运行?来自msdn“此计时器已优化,可用于Windows窗体应用程序,并且必须在窗口中使用。”用于此类工作为什么要在按钮回调中注册勾号事件?在其他位置注册它。这在UI线程上运行。这是您想要的吗?可能不是,对吗?UI线程上没有其他可用计时器。应用程序现在的行为如何?它至少有响应吗?@kclewis注册提交按钮中的勾选事件处理程序单击处理程序会导致位置\u警报\u计时器\u勾选()第一次单击按钮时调用一次,下一次调用两次,以此类推。它一遍又一遍地注册同一个回调函数,这导致在引发勾号事件时多次调用该回调函数。相反,在初始化时,+=该事件处理程序(可能在构造函数或其他一些setup()函数中)。这样,您将得到一个且只有一个对位置的函数调用。\u Alert\u Timer\u Tick()当计时器滴答声事件被触发时。我认为这个例子会起作用,但我希望通过尽可能少的重新定义来完成。你的aswer是一个很好的例子,我可能会在未来的实现中使用它,但现在对我来说可能有点复杂……我对这个问题不熟悉,正在寻找简单的解决方案,但这允许我这么做他在工作。嗯,恐怕没有一个真正简单可靠的解决方案……您可能可以使用示例项目中的一些代码。我总是觉得我无法控制在表单应用程序中调度任务时会发生什么。
private void Submit_Btn_Click(object sender, EventArgs e)
{
bool run = false;
if (Schedule_Chk.Checked == true)
{
run = true;
if (Recur_Txt.Text != "" || Recur_Txt.Text != "0")
{
while (run == true)
{
if ((Convert.ToDateTime(DateTime.Now.ToString("MM/dd/yyyy HH:mm")) <= Convert.ToDateTime(End_Date.Value.ToString("MM/dd/yyyy") + " " + Recur_Time_Txt.Text)))
{
DateTime dt1;
DateTime dt2;
TimeSpan ts = new TimeSpan(Convert.ToInt16(Recur_Txt.Text),0,0,0);
dt1 = Convert.ToDateTime(DateTime.Now.ToString("MM/dd/yyyy HH:mm"));
dt2 = Convert.ToDateTime(DateTime.Now.ToString("MM/dd/yyyy") + " " + Recur_Time_Txt.Text);
if (dt1 >= dt2)
{
Execute_Command();
Location_Alert_Timer.Interval = Convert.ToInt32((Convert.ToDateTime(DateTime.Now.ToString("MM/dd/yyyy") + " " + Recur_Time_Txt.Text + ":00.000").Add(ts) - DateTime.Now).TotalMilliseconds);
Location_Alert_Timer.Start();
timerActive = true;
TimerHold();
}
else
{
Location_Alert_Timer.Interval = Convert.ToInt32((Convert.ToDateTime(DateTime.Now.ToString("MM/dd/yyyy") + " " + Recur_Time_Txt.Text + ":00.000") - DateTime.Now).TotalMilliseconds);
singleuse = true;
Location_Alert_Timer.Start();
timerActive = true;
TimerHold();
MessageBox.Show(DateTime.Now.ToString());
MessageBox.Show(DateTime.Now.Add(ts).ToString());
MessageBox.Show((Convert.ToDateTime(DateTime.Now.Add(ts).ToString()) - DateTime.Now).TotalMilliseconds.ToString());
Location_Alert_Timer.Interval = Convert.ToInt32((Convert.ToDateTime(DateTime.Now.Add(ts).ToString()) - DateTime.Now).TotalMilliseconds);
Location_Alert_Timer.Start();
timerActive = true;
TimerHold();
}
}
else
{
Location_Alert_Timer.Stop();
run = false;
}
}
}
}
}
public void TimerHold()
{
while (timerActive)
{
Application.DoEvents();
}
}
void Location_Alert_Timer_Tick(object sender, EventArgs e)
{
if (singleuse)
{
if (uses < 1)
{
if (Convert.ToDateTime(DateTime.Now.ToString("MM/dd/yyyy HH:mm")) <= Convert.ToDateTime(End_Date.Value.ToString("MM/dd/yyyy") + " " + Recur_Time_Txt.Text))
{
uses++;
//DoItOnce();
Execute_Command();
}
else
{
timerActive = false;
}
}
else
{
singleuse = false;
timerActive = false;
Location_Alert_Timer.Stop();
}
}
else
{
if (Convert.ToDateTime(DateTime.Now.ToString("MM/dd/yyyy HH:mm")) <= Convert.ToDateTime(End_Date.Value.ToString("MM/dd/yyyy") + " " + Recur_Time_Txt.Text))
{
//DoIt();
Execute_Command();
}
else
{
timerActive = false;
}
}
}