Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > Visual C++/MFC/WTL > MFC поток и диалог


Автор: harimambura 5.2.2013, 19:36
Здравствуйте, форумчане.
Очень нуждаюсь в вашей помощи. вобщем вопрос следующий: необходимо в отдельном потоке отобразить окно диалога модально, при этом из основного потока использовать функции, описанные в классе этого диалога.

пробую делать так (общий вид кода, только основа):

Код
#include "InformationDlg.h"

CInformationDlg *InfoDlg= new CInformationDlg(L"");
//***************************************************
UINT ThreadProcess( LPVOID pParam )
{
    InfoDlg->DoModal();

    UINT nResult = 1;
    return nResult;
}

void myfunc() 
{
pThread = AfxBeginThread(ThreadProcess, this, THREAD_PRIORITY_NORMAL, 0,0 );
ASSERT(pThread);
InfoDlg->InitProgress2(1,12);
InfoDlg->SetCaption(L"txt");
InfoDlg->SetProgress2(6);
}

в хедере описан    CWinThread* pThread;

но после того, как поток запустился, на первой же функции InfoDlg->InitProgress2(1,12); бьет ошибку "an invalid argument was encountered", это в релизе, а в дебаге "Debug Assertion filed! file: f:\sp\vctools\vc7libs\ship\atlmfc\include\afxcmn.inl line:461".
далее выполнение функции myfunc обрывается, хоть диалог и отображается. Что не так?

Автор: Earnest 7.2.2013, 07:31
Не получится в рабочем потоке (как у тебя) запустить диалог. Ну то есть полноценно не получится. Диалогу, как и любому окну, нужен поток с циклом обработки сообщений.
Кроме того, обращаться к диалогу из другого потока тоже нехорошо, MFC такого не любит. Можно обращаться через сообщения, но не напрямую.
Если задача учебная, то совершенно дурацкая.

Автор: xTr1m 8.2.2013, 07:35
Насколько я могу судить, речь идет о диалоге хода выполнения некоторой задачи. И пусть конечно нехорошо запускать диалог в потоке, но вполне возможно.
Ошибка скорее всего вылазит потому, что сам диалог еще не успел "оформиться как окно", а вы ему уже функции дергаете. Для теста поставьте банальный Sleep(1000) после
Код

pThread = AfxBeginThread(ThreadProcess, this, THREAD_PRIORITY_NORMAL, 0,0 );

если все будет нормально, то просто нужно будет реализовать механизм ожидания (может быть подойдет WaitForInputIdle)

Автор: Earnest 12.2.2013, 08:41
Цитата(xTr1m @  8.2.2013,  08:35 Найти цитируемый пост)
 И пусть конечно нехорошо запускать диалог в потоке

Не "нехорошо", а нельзя. В Виндоус окно обрабатывает сообщения в своем потоке, и поток этот должен быть интерфейсным, т.е. иметь цикл обработки сообщений. Просто запустить диалог из рабочего потока, но который будет тем не менее работать в главном (или другом интерфейсном), можно, наверное, но криво очень. Описанная задача (т.е. запуск диалога, который отмечает ход рабочего потока) совсем не нуждается в этой кривоте. Диалог запускается в нормальном (главном) потоке, получает сообщения из рабочего и меняет прогресс. Вот и все. Можно сделать так, что рабочий поток по мере работы будет посылать 3 вида сообщений: я стартовал (запускайте диалог прогресса), текущий прогресс такой-то (обновите прогресс), я закончил с таким-то результатом. И никакой кривоты.

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)