как показать форму, пока процесс идет в текущей форме - PullRequest
0 голосов
/ 20 января 2012

У меня есть приложение для Windows в Visual Studio 2008 Framework 3.5, Мне нужно параллельное окно ожидания, в котором в окне происходит процесс, и в этом окне появляется другая форма с движущимся изображением (анимацией), точно как изображение .gif.

У меня есть 2 формы, на форме 2, при нажатии кнопки я выполняю длительный процесс, я хочу, чтобы мой 'frmWait' появлялся на экране, пока идет процесс в form2, и исчезал, когда он закончился. Когда появляется мое «frmWait», форма 2 не должна быть доступна пользователю.

мой код здесь. Форма 2

в процедуре SomeWork есть цикл for, который я написал, но на самом деле в программе это команды базы данных, которые выполняются в sqlserver, когда запрос выполняется на сервере, мои основные программы работают с остановкой до тех пор, пока сервер не завершит работу, после чего программа начнет работать указатель, между тем, программное обеспечение кажется, что это повешено.

    namespace WindowsFormsApplication1
    {
        public partial class Form2 : Form
        {
            public Form2()
            {
                InitializeComponent();
            }

            private void button1_Click(object sender, EventArgs e)
            {
                frmWait fw = new frmWait("Wait...",0);
                fw.Show();

                SomeWork();

                fw.Close();
            }

            private void SomeWork()
            {
                for (int x = 0; x < 99999999; x++)
                { }
            }
        }
    }

Ответы [ 6 ]

3 голосов
/ 20 января 2012

Вы должны выполнить длительный процесс в фоновом потоке. Это легко достигается с помощью BackgroundWorker .

Как только рабочий запущен, просто отобразите frmWait, используя frmWait.ShowDialog().

Когда работник уведомляет об окончании работы, закройте frmWait, например, используя frmWait.DialogResult=Cancel.

Вы можете воспользоваться событием ProgressChanged, чтобы сообщить о прогрессе в своей жизни.

И если пользователь нажимает кнопку Отмена в frmWait, просто наберите CancelAsync() на вашем рабочем столе.

Полный образец здесь .

2 голосов
/ 25 апреля 2012

Первое добавление ..

using System.Threading;

Я адаптировал ваш код выше для использования отдельного потока ..

private void button1_Click(object sender, EventArgs e) 
{ 
    this.SomeWork();             
}

Thread t;

private void SomeWork()
{
    frmWait fw = new frmWait("Wait...", 0);

    this.t = new Thread((ThreadStart)delegate()
    {

        for (int x = 0; x < 99999; x++)
        {
            Thread.Sleep(100);

            //Debug.WriteLine(x);
        }


        if (this != null && !this.IsDisposed) this.BeginInvoke((ThreadStart)delegate() { fw.Close(); });
    });

    this.t.Start();

    fw.ShowDialog(this);
}

Вы также можете обработать событие FormClosing, чтобы завершить поток, если пользователю было разрешено закрыть Form2 до завершения!

private void Form2_FormClosing(object sender, FormClosingEventArgs e)
{
    if (t != null && t.IsAlive) t.Abort();
} 
2 голосов
/ 20 января 2012

.NET 4 представила библиотеку параллельных задач, которая упрощает выполнение подобных задач.Вместо использования BackgroundWorker вы должны использовать System.Threading.Tasks.Task .В ответах на этот вопрос есть дополнительная информация: Замена параллельной библиотеки задач для BackgroundWorker?

0 голосов
/ 20 января 2012

Я не понял, что именно вы имеете в виду, но если вы хотите, чтобы до открытия frmWait ваш Form2 не был доступен для пользователя, используйте frmWait.ShowDialog (), и если вы хотите закрыть frmWait, когда конкретный процессзаканчивается в frmWait, используйте следующее

Process.WaitForExit();
this.Close();
0 голосов
/ 20 января 2012

Вы должны использовать BackgroundWorker в этом сценарии, чтобы переместить SomeWork деталь из основного потока пользовательского интерфейса

Переместите SomeWork(); деталь в отдельный DoWork метод BackgroundWorker. Таким образом, SomeWork будет выполняться BackgroundWorker в отдельном фоновом потоке. Затем в Background Work Completed событии, которое будет вызвано после завершения SomeWork, выполните fw.Close();

0 голосов
/ 20 января 2012

Вы можете использовать окно модального набора.поскольку он не позволяет взаимодействовать с другой формой (например, form2)

frmWait.ShowDialog();

, также попробуйте использовать Backgroud worker background worker , что упрощает выполнение фоновых процессов.

...