C# 修复拖放冻结资源管理器
我有一个应用程序,它允许在对数据执行可能非常长的操作之前将数据拖放到其中。这很好,但是,当我的应用程序正在处理时,资源管理器窗口会冻结。有没有什么方法可以在我拿到一份文件清单后立即“发布”它 我目前的代码是:C# 修复拖放冻结资源管理器,c#,winforms,C#,Winforms,我有一个应用程序,它允许在对数据执行可能非常长的操作之前将数据拖放到其中。这很好,但是,当我的应用程序正在处理时,资源管理器窗口会冻结。有没有什么方法可以在我拿到一份文件清单后立即“发布”它 我目前的代码是: private void MainForm_DragDrop(object sender, DragEventArgs e) { ClearTempFiles(); //Clear all files before populating st
private void MainForm_DragDrop(object sender, DragEventArgs e)
{
ClearTempFiles(); //Clear all files before populating
string[] files = (string[])e.Data.GetData(DataFormats.FileDrop); //Get the filepaths for the dragdrop data
List<string> toParse = new List<string>();
foreach (string file in files)
{
FileAttributes attr = File.GetAttributes(file);
if (attr.HasFlag(FileAttributes.Directory)) //If a folder has been included, add all files from within
{
toParse.AddRange(DirSearch(file));
}
else
{
toParse.Add(file); //Add files
}
}
CurrentJobData = new JobData(toParse); //Create new JobData from these files <---- Takes up to a few minutes with hundreds of files.
CurrentJobData.ToTree(treeView1); //Push this data to the TreeView
} //Handles the dragdrop of data, populating the solution
private void main form_DragDrop(对象发送方,DragEventArgs e)
{
ClearTempFiles();//在填充之前清除所有文件
string[]files=(string[])e.Data.GetData(DataFormats.FileDrop);//获取dragdrop数据的文件路径
List toParse=新列表();
foreach(文件中的字符串文件)
{
FileAttributes attr=File.GetAttributes(文件);
if(attr.hasvag(FileAttributes.Directory))//如果包含文件夹,则从中添加所有文件
{
toParse.AddRange(DirSearch(文件));
}
其他的
{
toParse.Add(文件);//添加文件
}
}
CurrentJobData=新的JobData(toParse);//从这些文件创建新的JobData您需要让事件运行到完成。由于DragDrop操作的性质,涉及的两个应用程序都需要确保操作已完成。它们只能判断DragDrop消息是否由任何一个消息泵处理。只要没有发生这种情况,资源管理器只能假设用户已完成仍在拖放。因此,正如评论中所建议的,请使用BackgroundWorker:
private void Form1_DragDrop(object sender, DragEventArgs e)
{
// gets all data from Explorer
string[] files = (string[])e.Data.GetData(DataFormats.FileDrop); //Get the filepaths for the dragdrop data
// don't block the UI thread, that prevents the
// processing of both Windows messages in Explorer and your app
// to complete, effectively blocking both of them
backgroundWorker1.RunWorkerAsync(files);
// if you want your form to be unavailable
// while processing takes place
// set Enabled to false on your form
this.Enabled = false;
}
您的DoWork
eventhandler现在将执行繁重的任务。请注意我如何设置DoWorkEventArgs
的Result
属性,以将您的作业数据发送到已完成的事件
// this all runs on a background, non-UI threed
private void backgroundWorker1_DoWork(object sender, DoWorkEventArgs e)
{
ClearTempFiles(); //Clear all files before populating
string[] files = (string[])e.Argument; // this is passed in from RunWorkerAsync
List<string> toParse = new List<string>();
foreach (string file in files)
{
FileAttributes attr = File.GetAttributes(file);
if (attr.HasFlag(FileAttributes.Directory)) //If a folder has been included, add all files from within
{
toParse.AddRange(DirSearch(file));
}
else
{
toParse.Add(file); //Add files
}
}
e.Result = new JobData(toParse); //Create new JobData from these files <---- Takes up to a few minutes with hundreds of files.
}
如果要报告进度,请确保使用ProgressChanged eventhandler,以便您处于UI线程上,并调用backgroundworker上的ReportProgress
方法来调用该处理程序。您应该在后台线程上执行长时间运行的任务。使用任务
或线程池
。您还可以使用。。我不希望程序本身继续运行或响应(除非进度条),直到此处理完成。这不是可以在后台完成的事情。我只是认为冻结Windows资源管理器有点不必要,我想知道是否有办法解决这一问题。
// this runs on the UI thread
private void backgroundWorker1_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
{
CurrentJobData = (JobData) e.Result;
CurrentJobData.ToTree(treeView1); //Push this data to the TreeView
// set Enabled to true on your controls
this.Enabled = true;
}