从后台工作者内部操纵ListView

时间:2012-08-25 23:55:16

标签: c# listview backgroundworker

我正在使用后台工作程序遍历ListView中的每个项目,并在单击按钮后对其进行操作:

private void bParsePosts_Click(object sender, EventArgs e)
{
    parseWorker.RunWorkerAsync(this.lvPostQueue);
}

然后,我有:

private void parseWorker_DoWork(object sender, DoWorkEventArgs e)
{
    // Loop through each item
    for (int i = 0; i < lvPostQueue.Items.Count; i++)
    {
        string title = lvPostQueue.Items[i].SubItems[0].ToString();
        string category = lvPostQueue.Items[i].SubItems[1].ToString();
        string url = lvPostQueue.Items[i].SubItems[2].ToString();

        lvPostQueue.Items[i].SubItems[3].Text = "Done";
    }
}

然而,我收到此错误:

Cross-thread operation not valid: Control 'lvPostQueue' accessed from a thread other than the thread it was created on.

如何从该后台工作程序中操作lvPostQueue控件?

感谢。

2 个答案:

答案 0 :(得分:0)

只需使用线程安全呼叫:http://msdn.microsoft.com/en-us/library/ms171728.aspx

示例:

// This event handler starts the form's  
        // BackgroundWorker by calling RunWorkerAsync. 
        // 
        // The Text property of the TextBox control is set 
        // when the BackgroundWorker raises the RunWorkerCompleted 
        // event. 
        private void setTextBackgroundWorkerBtn_Click(
            object sender, 
            EventArgs e)
        {
            this.backgroundWorker1.RunWorkerAsync();
        }

        // This event handler sets the Text property of the TextBox 
        // control. It is called on the thread that created the  
        // TextBox control, so the call is thread-safe. 
        // 
        // BackgroundWorker is the preferred way to perform asynchronous 
        // operations. 

        private void backgroundWorker1_RunWorkerCompleted(
            object sender, 
            RunWorkerCompletedEventArgs e)
        {
            this.textBox1.Text = 
                "This text was set safely by BackgroundWorker.";
        }

答案 1 :(得分:0)

正确的答案是:

private void bParsePosts_Click(object sender, EventArgs e)
{
    parseWorker.WorkerReportsProgress = true;
    parseWorker.ProgressChanged += new ProgressChangedEventHandler(worker_ProgressChanged);
    parseWorker.RunWorkerAsync();
}

private void parseWorker_DoWork(object sender, DoWorkEventArgs e)
{
    // Loop through each item
    for (int i = 0; i < lvPostQueue.Items.Count; i++)
    {
        string title = lvPostQueue.Items[i].SubItems[0].ToString();
        string category = lvPostQueue.Items[i].SubItems[1].ToString();
        string url = lvPostQueue.Items[i].SubItems[2].ToString();

        parseWorker.ReportProgress(i * 100 / lvPostQueue.Items.Count, i);
    }
}

void worker_ProgressChanged(object sender, ProgressChangedEventArgs e)
{
    var i = (int)e.UserState;
    lvPostQueue.Items[i].SubItems[3].Text = "Done";
}