Закрытие окна wpf, созданного в другом потоке из фонового рабочего WorkRunCompleted
Привет, есть продолжение к другому вопросу здесь
Вот краткое изложение
В приложении wpf на C# у меня был долгий процесс обновления удаленной базы данных. Для этого я создал фоновый рабочий. Однако я хотел открыть окно и запустить индикатор выполнения во время процедуры обновления базы данных. Все мои попытки достичь этого в моем главном окне с индикатором выполнения, установленным на Indeterminate, потерпели неудачу, так как эффект "свиста" на моем индикаторе прогресса не запустился в моем главном окне до тех пор, пока мой рабочий фоновый поток не закончился
Любая с помощью и этой статьи здесь мне удалось открыть новое окно в другом потоке и запустить фоновый рабочий и заставить индикатор выполнения правильно "качаться" и фоновая работа запускалась до конца. ОДНАКО, мой новый вопрос
Как закрыть окно индикатора выполнения (называемое progressDialog) после завершения фоновой работы?
Пожалуйста, имейте в виду, что я довольно новичок в этом, и примеры кода были бы очень ценны, и я ДУМАЮ, но я не уверен, что я хочу закрыть окно индикатора выполнения из области кода рабочего фона RunWorkerCompleted
вот мой код
Я настроил фонового работника как
public partial class MainWindow : Window
{
//Declare background workers
BackgroundWorker bwLoadCSV = new BackgroundWorker();
//Declare class variables
// some stuff
public MainWindow()
{
InitializeComponent();
//assign events to backgroundworkers
bwLoadCSV.WorkerReportsProgress = true;
bwLoadCSV.WorkerSupportsCancellation = true;
bwLoadCSV.DoWork += new DoWorkEventHandler(bwLoadCSV_DoWork);
bwLoadCSV.ProgressChanged += new ProgressChangedEventHandler(bwLoadCSV_ProgressChanged);
bwLoadCSV.RunWorkerCompleted += new RunWorkerCompletedEventHandler(bwLoadCSV_RunWorkerCompleted);
}
}
Я запускаю событие для события нажатия кнопки как;
private void CSV_Load_Click(object sender, RoutedEventArgs e)
///Function to read csv into datagrid
///
{
//Turn Cursor to wait
System.Windows.Forms.Cursor.Current = System.Windows.Forms.Cursors.WaitCursor;
Thread backgroundThread = new Thread(
new ThreadStart(() =>
{
ProgressDialog progressDialog = new ProgressDialog();
progressDialog.tbEvent.Text = "Loading CSV Data....";
progressDialog.progressBar1.IsIndeterminate = true;
progressDialog.ShowDialog();
}
));
backgroundThread.SetApartmentState(ApartmentState.STA);
backgroundThread.Start();
//Test connection to sql server
if (CHHoursDataProvider.IsDatabaseOnline() == false)
{
System.Windows.Forms.MessageBox.Show("Can not establish contact with sql server" + "\n" + "Contact IT", "Connection Error");
//Set UI picture
return;
}
//Set a control to update the user here
tbLoadDgStat.Visibility = Visibility.Visible;
//tbLoadDgStat.Text = "Getting data templete from Database...";
string FilePath = txFilePath.Text;
if (bwLoadCSV.IsBusy != true)
{
//load the context object with parameters for Background worker
bwCSVLoadContext Context = new bwCSVLoadContext();
Context.Site = cBChSite.Text;
Context.FilePath = txFilePath.Text;
Context.FileName = fileTest;
Context.Wageyear = cbWageYear.Text;
Context.Startdate = ((DateTime)dpStartDate.SelectedDate);
Context.Enddate = ((DateTime)dpEndDate.SelectedDate);
bwLoadCSV.RunWorkerAsync(Context);
}
}
Моя форма прогрессбаров progressDialog xaml и class это;
<Window x:Class="Test_Read_CSV.ProgressDialog"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="Progress Dialog" Height="115" Width="306" Name="ProgressPopup">
<Grid>
<ProgressBar Height="31" HorizontalAlignment="Left" Margin="12,33,0,0" Name="progressBar1" VerticalAlignment="Top" Width="250" x:FieldModifier="public" />
<TextBox Height="23" HorizontalAlignment="Left" Margin="7,4,0,0" Name="tbEvent" VerticalAlignment="Top" Width="254" IsReadOnly="True" IsEnabled="False" x:FieldModifier="public" />
</Grid>
class is
public partial class ProgressDialog : Window
{
public ProgressDialog()
{
WindowStartupLocation = WindowStartupLocation.CenterScreen;
InitializeComponent();
progressBar1.IsIndeterminate = true;
}
Мой фоновый рабочий код завершен
private void bwLoadCSV_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
{
bwCSVLoadContext Context = e.Result as bwCSVLoadContext;
Thread.Sleep(5000);
if ((e.Cancelled == true))
{
this.tbLoadDgStat.Text = "Canceled!";
System.Threading.Thread.Sleep(1000);
System.Windows.Forms.Cursor.Current = System.Windows.Forms.Cursors.Default;
tbLoadDgStat.Visibility = Visibility.Hidden;
}
else if (!(e.Error == null))
{
//this.tbProgress.Text = ("Error: " + e.Error.Message);
}
else
{
if (Context.LoadResult == true)
{
this.dgCSVData.DataContext = oTable.DefaultView;
btUpload.IsEnabled = true;
}
**//close the progressbar window some how here!!!**
//On the main window
this.tbLoadDgStat.Text = "Complete";
progressBar1.Value = 100;
System.Windows.Forms.Cursor.Current = System.Windows.Forms.Cursors.Default;
tbLoadDgStat.Visibility = Visibility.Hidden;
}
System.Windows.Forms.Cursor.Current = System.Windows.Forms.Cursors.Default;
}
1 ответ
Сделать фон на странице прогресса
Если вам нужно передать (и вернуть) объект, сделайте это в cgress.
private void click(object sender, RoutedEventArgs e)
{
Progress progressDialog = new Progress();
progressDialog.Show();
if (progressDialog != null) progressDialog = null;
}
namespace BackGroundWorkerShowDialog
{
/// <summary>
/// Interaction logic for Progress.xaml
/// </summary>
public partial class Progress : Window
{
BackgroundWorker bwLoadCSV = new BackgroundWorker();
public Progress()
{
InitializeComponent();
//assign events to backgroundworkers
bwLoadCSV.WorkerReportsProgress = true;
bwLoadCSV.WorkerSupportsCancellation = true;
bwLoadCSV.DoWork += new DoWorkEventHandler(backgroundWorker1_DoWork);
bwLoadCSV.ProgressChanged += new ProgressChangedEventHandler(backgroundWorker1_ProgressChanged);
bwLoadCSV.RunWorkerCompleted += new RunWorkerCompletedEventHandler(backgroundWorker1_RunWorkerCompleted);
if (bwLoadCSV.IsBusy != true)
{
// Start the asynchronous operation.
bwLoadCSV.RunWorkerAsync();
}
}
private void backgroundWorker1_DoWork(object sender, DoWorkEventArgs e)
{
BackgroundWorker worker = sender as BackgroundWorker;
for (int i = 1; i <= 10; i++)
{
if (worker.CancellationPending == true)
{
e.Cancel = true;
break;
}
else
{
// Perform a time consuming operation and report progress.
System.Threading.Thread.Sleep(500);
worker.ReportProgress(i * 10);
}
}
}
private void backgroundWorker1_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
{
if (e.Cancelled == true)
{
//resultLabel.Text = "Canceled!";
}
else if (e.Error != null)
{
//resultLabel.Text = "Error: " + e.Error.Message;
}
else
{
//resultLabel.Text = "Done: " + e.Error.Message;
}
this.Close();
}
private void backgroundWorker1_ProgressChanged(object sender,
ProgressChangedEventArgs e)
{
this.tbProgress.Text = e.ProgressPercentage.ToString();
}
}
}