其实很多资料已经对backgroundWorker控件讲的非常的详细了,这篇就当做自己的"脚印",放便以后自己的查看或复习
这个实例是做文件流的上传下载的部分功能,主要是通过线程来操作流并且加入了已使用时间、时间预测、进度展示
首先是选择文件这个非常简单,有点值的注意的是,通过RunWorkerAsync方法的传参(虽然不支持多个参数,但可以通过自己设计对象来解决)
private void button1_Click(object sender, EventArgs e)
{
openFileDialog1.ShowDialog();
if (System.IO.File.Exists(openFileDialog1.FileName))
{
backgroundWorker1.RunWorkerAsync(openFileDialog1.FileName as object);
}
}
{
openFileDialog1.ShowDialog();
if (System.IO.File.Exists(openFileDialog1.FileName))
{
backgroundWorker1.RunWorkerAsync(openFileDialog1.FileName as object);
}
}
接下来是线程的dowork事件,标注为红色的是已使用时间、时间预测计算,在这里可以看到TimeSpan类(以前自己没用过),它可以根据时、分、秒、毫秒来实例,在这里非常好用。
private void backgroundWorker1_DoWork(object sender, DoWorkEventArgs e)
{//这个方法和自己写线程时一样,是不能调用form的成员变量的。
FileStream fileStream = File.OpenRead(e.Argument.ToString());
long filelength = fileStream.Length % 100;
long nowread=0;
int progress = 0;
byte[] bytefile = new byte[4096];
backgroundWorker1.ReportProgress(0);
long last = DateTime.Now.Ticks;
while (true)
{
int bytesRead = fileStream.Read(bytefile, 0, 4096);
nowread+=bytesRead;
if (bytesRead == 0) break;
{//这个方法和自己写线程时一样,是不能调用form的成员变量的。
FileStream fileStream = File.OpenRead(e.Argument.ToString());
long filelength = fileStream.Length % 100;
long nowread=0;
int progress = 0;
byte[] bytefile = new byte[4096];
backgroundWorker1.ReportProgress(0);
long last = DateTime.Now.Ticks;
while (true)
{
int bytesRead = fileStream.Read(bytefile, 0, 4096);
nowread+=bytesRead;
if (bytesRead == 0) break;
if (progress != (int)(nowread * 100 / fileStream.Length))
{
progress = (int)(nowread * 100 / fileStream.Length);
{
progress = (int)(nowread * 100 / fileStream.Length);
TimeSpan tt = new TimeSpan(DateTime.Now.Ticks) - new TimeSpan(last);
double mini = tt.TotalMilliseconds * 100 / progress - tt.TotalMilliseconds;
double mini = tt.TotalMilliseconds * 100 / progress - tt.TotalMilliseconds;
TimeSpan alreadytime = TimeSpan.FromMilliseconds(tt.TotalMilliseconds);
TimeSpan leavetime = TimeSpan.FromMilliseconds(mini);
TimeSpan leavetime = TimeSpan.FromMilliseconds(mini);
string alreadytimeStr = "";
string leavetimeStr = "";
string leavetimeStr = "";
if (alreadytime.Days != 0)
alreadytimeStr += alreadytime.Days + "天 ";
if (alreadytime.Hours != 0)
alreadytimeStr += alreadytime.Hours + "小时 ";
if (alreadytime.Minutes != 0)
alreadytimeStr += alreadytime.Minutes + "分 ";
alreadytimeStr += alreadytime.Days + "天 ";
if (alreadytime.Hours != 0)
alreadytimeStr += alreadytime.Hours + "小时 ";
if (alreadytime.Minutes != 0)
alreadytimeStr += alreadytime.Minutes + "分 ";
alreadytimeStr += alreadytime.Seconds + "秒 ";
if (leavetime.Days != 0)
leavetimeStr += leavetime.Days + "天 ";
if (leavetime.Hours != 0)
leavetimeStr += leavetime.Hours + "小时 ";
if (leavetime.Minutes != 0)
leavetimeStr += leavetime.Minutes + "分 ";
leavetimeStr += leavetime.Days + "天 ";
if (leavetime.Hours != 0)
leavetimeStr += leavetime.Hours + "小时 ";
if (leavetime.Minutes != 0)
leavetimeStr += leavetime.Minutes + "分 ";
leavetimeStr += leavetime.Seconds + "秒 ";
string tt3 = alreadytimeStr + "|" + leavetimeStr;
backgroundWorker1.ReportProgress(progress
, tt3 as object);
}
}
}
backgroundWorker1.ReportProgress(100);
}
backgroundWorker1.ReportProgress(100);
}
最后的是一个展示,也比较简单,由上面dowork事件调用ReportProgress方法后触发的ProgressChanged事件。
private void backgroundWorker1_ProgressChanged(object sender, ProgressChangedEventArgs e)
{
label1.Text = e.ProgressPercentage.ToString();
progressBar1.Value = e.ProgressPercentage;
if (e.UserState != null)
{
label4.Text = e.UserState.ToString().Split('|')[0];
label6.Text = e.UserState.ToString().Split('|')[1];
}
}
{
label1.Text = e.ProgressPercentage.ToString();
progressBar1.Value = e.ProgressPercentage;
if (e.UserState != null)
{
label4.Text = e.UserState.ToString().Split('|')[0];
label6.Text = e.UserState.ToString().Split('|')[1];
}
}
其实这个实例并没有实现上传下载的存储,但那一部分的比较常见(橙色部分加一个把
bytefile存储就可以了)。