我用domodel创建了一个对话框,现象是,主对话框不能使用了,主线程好像被阻塞了,我已经创建另一个线程了
就算是阻塞,也应该是阻塞新创建的那个线程,怎么会是主线程?
18 个解决方案
#1
DoModal阻塞的是消息循环,主线程不能处理消息了,所以阻塞了
#2
线程应该不会被阻塞,只是DoModel是一个模态对话框,VC技术内幕里讲了,只有再响应完DoModel以后程序才一步一步的执行下一步骤,应该看你那个线程调用这个东西,那个线程才会阻塞
#3
你是以主线程中的窗口作为新线程对话框的父窗口的吧,模式对话框不会阻塞任何线程,也不会阻塞消息循环,只是他启动了一个内部的模式消息循环,父窗口的很多消息都被它屏蔽了。
#4
#5
up
#6
众说纷纭 ,反正DoModel会暂停执行知道处理完这个窗口的消息..所以我个人认为 调用他的线程会一直停在这个函数上直到DoModel结束
#7
主线程没有被阻塞,是你在线程中构造对话框对象时将父窗口参数给了NULL(缺省值),这样会把主窗口作为其父窗口,模态对话框会禁用其父窗口,所以主窗口不能用了。可以在构造对话框对象时指定父窗口为CWnd::GetDesktopWindow()。
#8
up
#9
DoModal的时候,dialog会EnableWindow(hWndParent, FALSE);
#10
up
#11
同意满天星大哥的说法
#12
调用对话框DoModal,主线程会执行到DoModal内部的消息循环处
该消息循环会屏蔽所有父窗口的界面消息
但是其他消息仍然路由到父窗口的消息处理
比如所父窗口的定时器消息依然处理
该消息循环会屏蔽所有父窗口的界面消息
但是其他消息仍然路由到父窗口的消息处理
比如所父窗口的定时器消息依然处理
#13
当然是阻塞主线程,你以为还能阻力得了新建的线程?你domodel是在主线程调用的,不是在新建的线程中调用,谁调用就阻塞谁.
#14
模式对话框有自己的消息循环
#15
DoModal阻塞主线程,这是常识,你可以用new出来的对话框就不会出现这种事情了。
#16
创建的子线程需要有自己的消息循环,含有消息循环的线程,称之为用户界面线程,以下是示例代码:
1.创建一个子对话框类:
class CMyDlg : public CDialog
{
DECLARE_DYNAMIC(CMyDlg)
public:
CMyDlg(CWnd* pParent = NULL); // standard constructor
virtual ~CMyDlg();
// Dialog Data
enum { IDD = IDD_MYDLG };
protected:
virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support
afx_msg void OnLButtonDown(UINT, CPoint);
DECLARE_MESSAGE_MAP()
};
BEGIN_MESSAGE_MAP(CMyDlg, CDialog)
ON_WM_LBUTTONDOWN()
END_MESSAGE_MAP()
void CMyDlg::OnLButtonDown(UINT, CPoint)
{
PostMessage(WM_CLOSE,0,0); //发送关闭窗体命令,消毁子对话框,从而退出子线程
}
2.添加用户界面线程类
class CUIThread1 : public CWinThread
{
DECLARE_DYNCREATE(CUIThread1)
protected:
CUIThread1(); // protected constructor used by dynamic creation
virtual ~CUIThread1();
public:
virtual BOOL InitInstance();
virtual int ExitInstance();
protected:
DECLARE_MESSAGE_MAP()
};
IMPLEMENT_DYNCREATE(CUIThread1, CWinThread)
BOOL CUIThread1::InitInstance()
{
m_pMainWnd=new CMyDlg; //将子对话框地址赋给m_pMainWnd,然后显示模态对话框
CMyDlg* pDlg=(CMyDlg*)m_pMainWnd;
pDlg->DoModal();
// TODO: perform and per-thread initialization here
return TRUE;
}
int CUIThread1::ExitInstance()
{
// TODO: perform any per-thread cleanup here
return CWinThread::ExitInstance();
}
BEGIN_MESSAGE_MAP(CUIThread1, CWinThread)
END_MESSAGE_MAP()
3.当主对话框需要启动用户线程时,使用如下代码:
CWinThread* m_UIThread=AfxBeginThread(RUNTIME_CLASS(CUIThread1),THREAD_PRIORITY_BELOW_NORMAL,0,0,NULL);
1.创建一个子对话框类:
class CMyDlg : public CDialog
{
DECLARE_DYNAMIC(CMyDlg)
public:
CMyDlg(CWnd* pParent = NULL); // standard constructor
virtual ~CMyDlg();
// Dialog Data
enum { IDD = IDD_MYDLG };
protected:
virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support
afx_msg void OnLButtonDown(UINT, CPoint);
DECLARE_MESSAGE_MAP()
};
BEGIN_MESSAGE_MAP(CMyDlg, CDialog)
ON_WM_LBUTTONDOWN()
END_MESSAGE_MAP()
void CMyDlg::OnLButtonDown(UINT, CPoint)
{
PostMessage(WM_CLOSE,0,0); //发送关闭窗体命令,消毁子对话框,从而退出子线程
}
2.添加用户界面线程类
class CUIThread1 : public CWinThread
{
DECLARE_DYNCREATE(CUIThread1)
protected:
CUIThread1(); // protected constructor used by dynamic creation
virtual ~CUIThread1();
public:
virtual BOOL InitInstance();
virtual int ExitInstance();
protected:
DECLARE_MESSAGE_MAP()
};
IMPLEMENT_DYNCREATE(CUIThread1, CWinThread)
BOOL CUIThread1::InitInstance()
{
m_pMainWnd=new CMyDlg; //将子对话框地址赋给m_pMainWnd,然后显示模态对话框
CMyDlg* pDlg=(CMyDlg*)m_pMainWnd;
pDlg->DoModal();
// TODO: perform and per-thread initialization here
return TRUE;
}
int CUIThread1::ExitInstance()
{
// TODO: perform any per-thread cleanup here
return CWinThread::ExitInstance();
}
BEGIN_MESSAGE_MAP(CUIThread1, CWinThread)
END_MESSAGE_MAP()
3.当主对话框需要启动用户线程时,使用如下代码:
CWinThread* m_UIThread=AfxBeginThread(RUNTIME_CLASS(CUIThread1),THREAD_PRIORITY_BELOW_NORMAL,0,0,NULL);
#17
mark
#18
进来学习咯
#1
DoModal阻塞的是消息循环,主线程不能处理消息了,所以阻塞了
#2
线程应该不会被阻塞,只是DoModel是一个模态对话框,VC技术内幕里讲了,只有再响应完DoModel以后程序才一步一步的执行下一步骤,应该看你那个线程调用这个东西,那个线程才会阻塞
#3
你是以主线程中的窗口作为新线程对话框的父窗口的吧,模式对话框不会阻塞任何线程,也不会阻塞消息循环,只是他启动了一个内部的模式消息循环,父窗口的很多消息都被它屏蔽了。
#4
#5
up
#6
众说纷纭 ,反正DoModel会暂停执行知道处理完这个窗口的消息..所以我个人认为 调用他的线程会一直停在这个函数上直到DoModel结束
#7
主线程没有被阻塞,是你在线程中构造对话框对象时将父窗口参数给了NULL(缺省值),这样会把主窗口作为其父窗口,模态对话框会禁用其父窗口,所以主窗口不能用了。可以在构造对话框对象时指定父窗口为CWnd::GetDesktopWindow()。
#8
up
#9
DoModal的时候,dialog会EnableWindow(hWndParent, FALSE);
#10
up
#11
同意满天星大哥的说法
#12
调用对话框DoModal,主线程会执行到DoModal内部的消息循环处
该消息循环会屏蔽所有父窗口的界面消息
但是其他消息仍然路由到父窗口的消息处理
比如所父窗口的定时器消息依然处理
该消息循环会屏蔽所有父窗口的界面消息
但是其他消息仍然路由到父窗口的消息处理
比如所父窗口的定时器消息依然处理
#13
当然是阻塞主线程,你以为还能阻力得了新建的线程?你domodel是在主线程调用的,不是在新建的线程中调用,谁调用就阻塞谁.
#14
模式对话框有自己的消息循环
#15
DoModal阻塞主线程,这是常识,你可以用new出来的对话框就不会出现这种事情了。
#16
创建的子线程需要有自己的消息循环,含有消息循环的线程,称之为用户界面线程,以下是示例代码:
1.创建一个子对话框类:
class CMyDlg : public CDialog
{
DECLARE_DYNAMIC(CMyDlg)
public:
CMyDlg(CWnd* pParent = NULL); // standard constructor
virtual ~CMyDlg();
// Dialog Data
enum { IDD = IDD_MYDLG };
protected:
virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support
afx_msg void OnLButtonDown(UINT, CPoint);
DECLARE_MESSAGE_MAP()
};
BEGIN_MESSAGE_MAP(CMyDlg, CDialog)
ON_WM_LBUTTONDOWN()
END_MESSAGE_MAP()
void CMyDlg::OnLButtonDown(UINT, CPoint)
{
PostMessage(WM_CLOSE,0,0); //发送关闭窗体命令,消毁子对话框,从而退出子线程
}
2.添加用户界面线程类
class CUIThread1 : public CWinThread
{
DECLARE_DYNCREATE(CUIThread1)
protected:
CUIThread1(); // protected constructor used by dynamic creation
virtual ~CUIThread1();
public:
virtual BOOL InitInstance();
virtual int ExitInstance();
protected:
DECLARE_MESSAGE_MAP()
};
IMPLEMENT_DYNCREATE(CUIThread1, CWinThread)
BOOL CUIThread1::InitInstance()
{
m_pMainWnd=new CMyDlg; //将子对话框地址赋给m_pMainWnd,然后显示模态对话框
CMyDlg* pDlg=(CMyDlg*)m_pMainWnd;
pDlg->DoModal();
// TODO: perform and per-thread initialization here
return TRUE;
}
int CUIThread1::ExitInstance()
{
// TODO: perform any per-thread cleanup here
return CWinThread::ExitInstance();
}
BEGIN_MESSAGE_MAP(CUIThread1, CWinThread)
END_MESSAGE_MAP()
3.当主对话框需要启动用户线程时,使用如下代码:
CWinThread* m_UIThread=AfxBeginThread(RUNTIME_CLASS(CUIThread1),THREAD_PRIORITY_BELOW_NORMAL,0,0,NULL);
1.创建一个子对话框类:
class CMyDlg : public CDialog
{
DECLARE_DYNAMIC(CMyDlg)
public:
CMyDlg(CWnd* pParent = NULL); // standard constructor
virtual ~CMyDlg();
// Dialog Data
enum { IDD = IDD_MYDLG };
protected:
virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support
afx_msg void OnLButtonDown(UINT, CPoint);
DECLARE_MESSAGE_MAP()
};
BEGIN_MESSAGE_MAP(CMyDlg, CDialog)
ON_WM_LBUTTONDOWN()
END_MESSAGE_MAP()
void CMyDlg::OnLButtonDown(UINT, CPoint)
{
PostMessage(WM_CLOSE,0,0); //发送关闭窗体命令,消毁子对话框,从而退出子线程
}
2.添加用户界面线程类
class CUIThread1 : public CWinThread
{
DECLARE_DYNCREATE(CUIThread1)
protected:
CUIThread1(); // protected constructor used by dynamic creation
virtual ~CUIThread1();
public:
virtual BOOL InitInstance();
virtual int ExitInstance();
protected:
DECLARE_MESSAGE_MAP()
};
IMPLEMENT_DYNCREATE(CUIThread1, CWinThread)
BOOL CUIThread1::InitInstance()
{
m_pMainWnd=new CMyDlg; //将子对话框地址赋给m_pMainWnd,然后显示模态对话框
CMyDlg* pDlg=(CMyDlg*)m_pMainWnd;
pDlg->DoModal();
// TODO: perform and per-thread initialization here
return TRUE;
}
int CUIThread1::ExitInstance()
{
// TODO: perform any per-thread cleanup here
return CWinThread::ExitInstance();
}
BEGIN_MESSAGE_MAP(CUIThread1, CWinThread)
END_MESSAGE_MAP()
3.当主对话框需要启动用户线程时,使用如下代码:
CWinThread* m_UIThread=AfxBeginThread(RUNTIME_CLASS(CUIThread1),THREAD_PRIORITY_BELOW_NORMAL,0,0,NULL);
#17
mark
#18
进来学习咯