Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
393 views
in Technique[技术] by (71.8m points)

c# - BackgroundWorker WPF difficulties with Progress Bar

I am developing a WPF, C# application and I have to read a very big CSV file and write to a database. This process takes a long time so I want to at least show a progress bar that grows in size as it nears completition.

Now, I have the following code at the top:

private readonly BackgroundWorker worker = new BackgroundWorker();

Then inside the loop I have this:

worker.WorkerReportsProgress = true;
worker.ReportProgress((100 * i) / 10000);

and I have a private sub like this:

private void worker_ProgressChanged(object sender, ProgressChangedEventArgs e)
{
    prgBar.Value = Math.Min(e.ProgressPercentage, 100);
}

Yet I don't see the progress bar updating or anything happening, program still hangs. Am I doing something wrong?

UPDATE: Tried the MSDN guide here http://msdn.microsoft.com/en-us/library/cc221403%28v=vs.95%29.aspx and I somehow failed to get it working with that example. I adjusted the looping part of course. Heh. It still stays idle and nothing updates. Heck, all I want to do is get a small counter that increases every time a line is read and added.

UPDATED CODE:

    private BackgroundWorker bw = new BackgroundWorker();

    public Process()
    {


        bw.WorkerReportsProgress = true;
        bw.WorkerSupportsCancellation = true;
        bw.DoWork += new DoWorkEventHandler(bw_DoWork);
        bw.ProgressChanged += new ProgressChangedEventHandler(bw_ProgressChanged);
        bw.RunWorkerCompleted += new RunWorkerCompletedEventHandler(bw_RunWorkerCompleted);
    }


    private void bw_DoWork(object sender, DoWorkEventArgs e)
    {
        BackgroundWorker worker = sender as BackgroundWorker;


                // Perform a time consuming operation and report progress.



                int d = 0;
                Microsoft.Win32.OpenFileDialog dlg = new Microsoft.Win32.OpenFileDialog();



                // Set filter for file extension and default file extension 
                dlg.DefaultExt = ".csv";
                dlg.Filter = "CSV File (*.csv)|*.csv";
                dlg.Title = "file";


                // Display OpenFileDialog by calling ShowDialog method 
                Nullable<bool> result = dlg.ShowDialog();
                if (result == true)
                {
                    // Open document 
                    string filename = dlg.FileName;
                    List<String[]> fileContent = new List<string[]>();

                    using (FileStream reader = File.OpenRead(@filename)) // mind the encoding - UTF8
                    using (TextFieldParser parser = new TextFieldParser(reader))
                    {

                        using (SqlConnection conn = new SqlConnection(Classes.PublicVariables.Connection))
                        {

                            parser.Delimiters = new[] { "," };
                            parser.HasFieldsEnclosedInQuotes = true;
                            while (!parser.EndOfData)
                            {

                                    string[] line = parser.ReadFields();
                                    fileContent.Add(line);

                                    SqlCommand comm = QUERYANDPARAMETERS

                                    d += 1;
                                    comm.ExecuteNonQuery();
                                    worker.ReportProgress((d * 10));


                        }
                    }

                }


        }


           private void bw_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
    {
lblCount.Content = "Complete";
    }
    private void bw_ProgressChanged(object sender, ProgressChangedEventArgs e)
    {
        this.lblCount.Content = (e.ProgressPercentage.ToString() + "%");
    }

I am getting an excerption when the worker runs.

 An exception of type 'System.NullReferenceException' occurred inSolution.exe but was not handled in user code

Additional information: Object reference not set to an instance of an object.

UPDATE3

Got it working! All I needed was the same code as above but this:

        if (bw.IsBusy != true)
        {
            bw.RunWorkerAsync();
        }
        else
        {
            bw_DoWork(null, null);
        }

In the event handler for the button press.

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Answer

0 votes
by (71.8m points)

This will not compile as-is, but should get you started in the right direction:

private readonly BackgroundWorker worker
    = new BackgroundWorker { WorkerReportsProgress = true };

public MainWindow()
{
    InitializeComponent();

    worker.DoWork += worker_DoWork;
    worker.ProgressChanged += worker_ProgressChanged;
}

private void worker_DoWork(object sender, DoWorkEventArgs doWorkEventArgs)
{
    // Do some long process, break it up into a loop so you can periodically
    //  call worker.ReportProgress()

    worker.ReportProgress(i);  // Pass back some meaningful value
}

private void worker_ProgressChanged(object sender, ProgressChangedEventArgs e)
{
    prgBar.Value = Math.Min(e.ProgressPercentage, 100);
}

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...