WPF c#progressbar只想在messagebox之后更新

WPF c#progressbar只想在messagebox之后更新,c#,wpf,progress-bar,invoke,dispatcher,C#,Wpf,Progress Bar,Invoke,Dispatcher,正如我所看到的,许多人与progressbar斗争。我一直在广泛地寻找解决我问题的方法。但不知何故,stackoverflow上的所有解决方案都不适合我。所以我想是时候问你们我的第一个问题了 在这个示例代码中,我拥有与WPF中给出的progressbar有关的所有内容。代码可以工作,从progressbar中删除,以可视化方式更新其值。如果每次“progress”对象更改时调用MessageBox,则主窗口将更新progressbar,并按原样显示 也许我把代码编错了?我没有得到任何例外或错误。

正如我所看到的,许多人与progressbar斗争。我一直在广泛地寻找解决我问题的方法。但不知何故,stackoverflow上的所有解决方案都不适合我。所以我想是时候问你们我的第一个问题了

在这个示例代码中,我拥有与WPF中给出的progressbar有关的所有内容。代码可以工作,从progressbar中删除,以可视化方式更新其值。如果每次“progress”对象更改时调用MessageBox,则主窗口将更新progressbar,并按原样显示

也许我把代码编错了?我没有得到任何例外或错误。除了progressbar之外,一切都正常工作

下面的代码示例用于查看

#region Progressbar

    /// <summary>
    /// Initializes the use of the Progressbar.
    /// </summary>
    private void startProgressbar()
    {
        progress = 0;
        gridProgressbar.Visibility = Visibility.Visible;
    }

    /// <summary>
    /// Ends the Progressbar by making it invisible for the user.
    /// </summary>
    private void stopProgressbar()
    {
        gridProgressbar.Visibility = Visibility.Collapsed;
    }

    /// <summary>
    /// Shows the progress in %.
    /// </summary>
    public double progress = 0.0;

    /// <summary>
    /// Calculates the current progress for the progressbar in %.
    /// </summary>
    /// <param name="value">Number of finished data.</param>
    /// <param name="maximum">Maximum number of data.</param>
    [MethodImpl(MethodImplOptions.Synchronized)]
    private void setProgress(int value, int maximum)
    {
        double v = value, m = maximum;
        if (m > 0.0 && m >= v)
            progress = v / m * 100.0;
        else
            progress = 0.0;

        txtProgressbarWorking.Content = "Working... " + v + "/" + m;

        //progressbar.Value = progress;
        //Thread.Sleep(100); // FOR await 

        //MessageBox.Show("" + (int)progress);
    }

    #region Backgroundworker

    /// <summary>
    /// Backgroundworker.
    /// </summary>
    BackgroundWorker worker;

    /// <summary>
    /// After the MainWindow has finished rendering, 
    /// the BackgroundWorker will be set up and be started.
    /// </summary>
    /// <param name="sender"></param>
    /// <param name="e"></param>
    private void Window_ContentRendered(object sender, EventArgs e)
    {
        worker = new BackgroundWorker();
        worker.WorkerReportsProgress = true;
        worker.WorkerSupportsCancellation = true;
        worker.DoWork += worker_DoWork;
        worker.ProgressChanged += worker_ProgressChanged;

        worker.RunWorkerAsync();
    }

    /// <summary>
    /// Work-function of the BackgroundWorker.
    /// </summary>
    /// <param name="sender"></param>
    /// <param name="e"></param>
    void worker_DoWork(object sender, DoWorkEventArgs e)
    {
        //MessageBox.Show("hi");
        for (;;)
        {
            Dispatcher.BeginInvoke(DispatcherPriority.Normal, new ThreadStart(() =>
            {
                try
                {
                    if (gridProgressbar.Visibility == Visibility.Visible)
                    {
                        (sender as BackgroundWorker).ReportProgress((int)progress);
                    }
                }
                catch (Exception a)
                {
                    MessageBox.Show(a.Message);
                }
            }));
            Thread.Sleep(1);
        }
    }

    /// <summary>
    /// This function updates the progress to the progressbar.
    /// </summary>
    /// <param name="sender"></param>
    /// <param name="e"></param>
    void worker_ProgressChanged(object sender, ProgressChangedEventArgs e)
    {
        progressbar.Value = e.ProgressPercentage;
        //Application.Current.Dispatcher.Invoke(new Action(() => this.progressbar.Value = e.ProgressPercentage), DispatcherPriority.Render);
        //Application.Current.Dispatcher.Invoke(delegate () { }, DispatcherPriority.Render);
        //progressbar.InvalidateVisual();
    }

    /// <summary>
    /// When User closes the whole program, we need to tell the
    /// BackgroundWorker to stop his work.
    /// </summary>
    /// <param name="sender"></param>
    /// <param name="e"></param>
    private void Window_Closing(object sender, CancelEventArgs e)
    {
        worker.CancelAsync();
    }

    #endregion

    #endregion
例如。这对我来说非常有效,我设法没有任何性能问题。progressbar现在更新得非常顺利


感谢所有帮助过我的人。谢谢你

你能告诉我你的目标是什么吗。是否要在Messagebox的后面显示progressbar?progressbar位于MainWindow类自己的网格中。根据我的理解,随着可见性的改变,如果我读取了文件,它将是可见的,如果没有,它将是折叠的。在调用
startProgressbar
时,它会在UI上显示Progressbar,但在调用
openfiledialog.show
后,它会触发模式窗口,导致Progressbar在UI中隐藏而不显示。这就是真正的问题吗?不,progressbar和所有内容都按预期可见。但是如果我在openfiledialog.show之后调用startProgressbar,它将不可见。但这不是这里的主要问题。(我只是说,这是一个小错误,可以忽略)说得很简单:我有一个excel文件,其中我正在读取23行数据。setProgressbar用于设置双值“进度”。(这23行中有多少行已经写入我的数据表中。该值介于0和100之间(这是显而易见的原因)。我可以看到progressbar,但它没有变为绿色。您的意思是在调用
openfiledialog.show之后,progressbar没有更新状态
/// <summary>
    /// Get's the whole data from an excel file into a DataTable object.
    /// The whole data is shown in a DataGrid.
    /// </summary>
    private void getArticleUpdateExcelData()
    {
        Excel.Application appExl;
        Excel.Workbook workbook;
        Excel.Worksheet NwSheet;
        Excel.Range ShtRange;
        appExl = new Excel.Application();

        **startProgressbar();**

        //Opening Excel file
        string filename = getExcelFileName().Result;
        workbook = appExl.Workbooks.Open(filename);

        NwSheet = (Excel.Worksheet)workbook.Sheets.get_Item(1);

        ShtRange = NwSheet.UsedRange; //gives the used cells in sheet

        //Reading Excel file.
        //Creating datatable to read the containt of the Sheet in File.
        table = new DataTable();
        for (int i = 0; i < ShtRange.Columns.Count; ++i)
            table.Columns.Add("" + i);

        for (int row = 1; row <= ShtRange.Rows.Count; ++row)
        {
            DataRow dr = table.NewRow();
            for (int column = 1; column <= ShtRange.Columns.Count; ++column)
                dr[column - 1] = (ShtRange.Cells[row, column] as Excel.Range).Text.ToString();
            table.Rows.Add(dr); // adding Row into DataTable

            //progressbar.Value = (row - 1) / (ShtRange.Columns.Count - 1) * 100.0;

            **setProgress(row - 1, ShtRange.Rows.Count - 1);**

            //progressbar.InvalidateArrange();
        }

        table.AcceptChanges();

        **stopProgressbar();**

        dataGrid.DataContext = table.DefaultView;

        workbook.Close(false);
        appExl.Quit();
    }
this.Dispatcher.Invoke((Action)(() =>
            {
                workbook.Close(false);
                appExl.Quit();

                table.AcceptChanges();
                dataGrid.DataContext = table.DefaultView;
                this.WindowStyle = WindowStyle.SingleBorderWindow;
            }));