form bar c# .net winforms loading

bar - progress dialog c#



¿Cómo puedo mostrar un control de carga mientras un proceso está esperando a que finalice? (2)

Crea un hilo, que simplemente establece dos propiedades y luego termina. El t.Abort probablemente no hará nada, ya que el hilo habrá salido para ese momento. Peor aún, importa el archivo de Excel en el hilo de la interfaz de usuario, que bloquea cualquier animación y congela la interfaz de usuario completa.

Así es como debes hacerlo:

Observación: Por supuesto, si su formulario responde, debe deshabilitar / habilitar los controles y preparar para el caso lo que sucede si su formulario se cierra durante la carga.

1. Usando hilos

Si realmente quieres usar hilos explícitamente, hazlo así:

public partial class Form1 : Form { public Form1() { InitializeComponent(); } private Thread workerThread = null; private void btnImport_Click(object sender, EventArgs e) { // start the animation (I used a progress bar, start your circle here) progressBar1.Visible = true; progressBar1.Style = ProgressBarStyle.Marquee; // start the job and the timer, which polls the thread btnImport.Enabled = false; workerThread = new Thread(LoadExcel); workerThread.Start(); timer1.Interval = 100; timer1.Start(); } private void LoadExcel() { // some work takes 5 sec Thread.Sleep(5000); } private void timer1_Tick(object sender, EventArgs e) { if (workerThread == null) { timer1.Stop(); return; } // still works: exiting if (workerThread.IsAlive) return; // finished btnImport.Enabled = true; timer1.Stop(); progressBar1.Visible = false; workerThread = null; } }

2. Trabajador de antecedentes

BackgroundWorker puede lanzar un evento cuando haya terminado:

public partial class Form1 : Form { public Form1() { InitializeComponent(); backgroundWorker1.DoWork += BackgroundWorker1_DoWork; backgroundWorker1.RunWorkerCompleted += BackgroundWorker1_RunWorkerCompleted; } private void btnImport_Click(object sender, EventArgs e) { // start the animation progressBar1.Visible = true; progressBar1.Style = ProgressBarStyle.Marquee; // start the job btnImport.Enabled = false; backgroundWorker1.RunWorkerAsync(); } private void BackgroundWorker1_DoWork(object sender, DoWorkEventArgs e) { LoadExcel(); } private void BackgroundWorker1_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e) { btnImport.Enabled = true; progressBar1.Visible = false; } private void LoadExcel() { // some work takes 5 sec Thread.Sleep(5000); } }

3. Usando async-await

Este es el más simple.

public partial class Form1 : Form { public Form1() { InitializeComponent(); } private async void btnImport_Click(object sender, EventArgs e) { // start the waiting animation progressBar1.Visible = true; progressBar1.Style = ProgressBarStyle.Marquee; // simply start and await the loading task btnImport.Enabled = false; await Task.Run(() => LoadExcel()); // re-enable things btnImport.Enabled = true; progressBar1.Visible = false; } private void LoadExcel() { // some work takes 5 sec Thread.Sleep(5000); } }

Decidí usar este componente de terceros para hacer un control de carga simple en mi formulario de Windows.

http://www.codeproject.com/Articles/14841/How-to-write-a-loading-circle-animation-in-NET

Esto funciona bien cuando se activa y desactiva cambiando la propiedad "Activo" a verdadero o falso en una sola solicitud (una por vez). El problema es cuando un proceso está esperando ser servido, y pretendo activar el control de carga antes de que comience el proceso y apagarlo cuando "creo" que el proceso tiene que finalizar. Cuando lo hago, la carga de la imagen se muestra como una imagen estática. (Sin animación).

Lo siento por esta pregunta, soy nuevo en C #. Pero creo que necesito usar hilos o algo similar.

Entonces mi código general es este:

using [libraries here]...; namespace [namespace here] { Public partial class Form1 : Form { public Form1() { InitializeComponent(); this.loadingCircle1.Visible = false; } private void button1_Click(object sender, EventArgs e) { Thread t = new Thread(new ThreadStart(showLoading)); this.loadingCircle1.Visible = true; t.Start(); //Import an Excel t.Abort(); } public void showLoading() { loadingCircle1.Active = true; loadingCircle1.RotationSpeed = 10; } } }

Pero Always the Loading se muestra como una imagen estática sin la animación.


Recomiendo usar async / await (para C # 5.0):

private void button1_Click(object sender, EventArgs e){ ImportAsync(); } private async Task ImportAsync(){ // UI-thread showLoading(); this.loadingCircle1.Visible = true; // wait until task will be finished await Task.Run(() => { // different non-blocking thread for all the hard work, but without UI-stuff // import an Excel }); // going back to UI-thread this.loadingCircle1.Visible = false; }