227 lines
4.8 KiB
C++
227 lines
4.8 KiB
C++
|
/**********************************************************************/
|
||
|
/** Microsoft Windows/NT **/
|
||
|
/** Copyright(c) Microsoft Corporation, 1997 - 1998 **/
|
||
|
/**********************************************************************/
|
||
|
|
||
|
/*
|
||
|
busydlg.cpp
|
||
|
base class for the busy dialog
|
||
|
|
||
|
FILE HISTORY:
|
||
|
|
||
|
*/
|
||
|
|
||
|
#include "stdafx.h"
|
||
|
#include "busydlg.h"
|
||
|
|
||
|
/////////////////////////////////////////////////////////////////////////////
|
||
|
// CWorkerThread
|
||
|
|
||
|
CWorkerThread::CWorkerThread()
|
||
|
{
|
||
|
m_bAutoDelete = FALSE;
|
||
|
m_bAbandoned = FALSE;
|
||
|
m_hEventHandle = NULL;
|
||
|
::InitializeCriticalSection(&m_cs);
|
||
|
m_hWnd = NULL;
|
||
|
}
|
||
|
|
||
|
CWorkerThread::~CWorkerThread()
|
||
|
{
|
||
|
::DeleteCriticalSection(&m_cs);
|
||
|
if (m_hEventHandle != NULL)
|
||
|
{
|
||
|
VERIFY(::CloseHandle(m_hEventHandle));
|
||
|
m_hEventHandle = NULL;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
BOOL CWorkerThread::Start(HWND hWnd)
|
||
|
{
|
||
|
ASSERT(m_hWnd == NULL);
|
||
|
ASSERT(::IsWindow(hWnd));
|
||
|
m_hWnd = hWnd;
|
||
|
|
||
|
ASSERT(m_hEventHandle == NULL); // cannot call start twice or reuse the same C++ object
|
||
|
m_hEventHandle = ::CreateEvent(NULL,TRUE /*bManualReset*/,FALSE /*signalled*/, NULL);
|
||
|
if (m_hEventHandle == NULL)
|
||
|
return FALSE;
|
||
|
return CreateThread();
|
||
|
}
|
||
|
|
||
|
void CWorkerThread::Abandon()
|
||
|
{
|
||
|
Lock();
|
||
|
OnAbandon();
|
||
|
m_bAutoDelete = TRUE;
|
||
|
m_bAbandoned = TRUE;
|
||
|
Unlock();
|
||
|
}
|
||
|
|
||
|
|
||
|
BOOL CWorkerThread::IsAbandoned()
|
||
|
{
|
||
|
Lock();
|
||
|
BOOL b = m_bAbandoned;
|
||
|
Unlock();
|
||
|
return b;
|
||
|
}
|
||
|
|
||
|
BOOL CWorkerThread::PostMessageToWnd(UINT Msg, WPARAM wParam, LPARAM lParam)
|
||
|
{
|
||
|
BOOL b = IsAbandoned();
|
||
|
if (b)
|
||
|
return TRUE; // no need to post
|
||
|
ASSERT(::IsWindow(m_hWnd));
|
||
|
return ::PostMessage(m_hWnd, Msg, wParam, lParam);
|
||
|
}
|
||
|
|
||
|
void CWorkerThread::WaitForExitAcknowledge()
|
||
|
{
|
||
|
BOOL b = IsAbandoned();
|
||
|
if (b)
|
||
|
return;
|
||
|
VERIFY(WAIT_OBJECT_0 == ::WaitForSingleObject(m_hEventHandle,INFINITE));
|
||
|
}
|
||
|
|
||
|
/////////////////////////////////////////////////////////////////////////////
|
||
|
// CDlgWorkerThread
|
||
|
|
||
|
CDlgWorkerThread::CDlgWorkerThread()
|
||
|
{
|
||
|
m_dwErr = 0x0;
|
||
|
}
|
||
|
|
||
|
|
||
|
BOOL CDlgWorkerThread::Start(CLongOperationDialog* pDlg)
|
||
|
{
|
||
|
ASSERT(pDlg != NULL);
|
||
|
HWND hWnd = pDlg->GetSafeHwnd();
|
||
|
return CWorkerThread::Start(hWnd);
|
||
|
}
|
||
|
|
||
|
BOOL CDlgWorkerThread::PostMessageToDlg()
|
||
|
{
|
||
|
return PostMessageToWnd(CLongOperationDialog::s_nNotificationMessage,
|
||
|
(WPARAM)0, (LPARAM)0);
|
||
|
}
|
||
|
|
||
|
|
||
|
int CDlgWorkerThread::Run()
|
||
|
{
|
||
|
// do the stuff
|
||
|
OnDoAction();
|
||
|
VERIFY(PostMessageToDlg());
|
||
|
WaitForExitAcknowledge();
|
||
|
//TRACE(_T("exiting\n"));
|
||
|
return 0;
|
||
|
|
||
|
}
|
||
|
|
||
|
|
||
|
/////////////////////////////////////////////////////////////////////////////
|
||
|
// CLongOperationDialog dialog
|
||
|
|
||
|
UINT CLongOperationDialog::s_nNotificationMessage = WM_USER + 100;
|
||
|
|
||
|
CLongOperationDialog::CLongOperationDialog(CDlgWorkerThread* pThreadObj,
|
||
|
UINT nAviID)
|
||
|
: CDialog(IDD_BUSY, NULL),
|
||
|
m_bCancel(TRUE)
|
||
|
{
|
||
|
ASSERT(pThreadObj != NULL);
|
||
|
m_bAbandoned = TRUE;
|
||
|
m_pThreadObj = pThreadObj;
|
||
|
m_nAviID = nAviID;
|
||
|
}
|
||
|
|
||
|
CLongOperationDialog::~CLongOperationDialog()
|
||
|
{
|
||
|
if(m_pThreadObj != NULL)
|
||
|
{
|
||
|
delete m_pThreadObj;
|
||
|
m_pThreadObj = NULL;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
BOOL CLongOperationDialog::LoadTitleString(UINT nID)
|
||
|
{
|
||
|
AFX_MANAGE_STATE(AfxGetStaticModuleState());
|
||
|
return m_strTitle.LoadString(nID);
|
||
|
}
|
||
|
|
||
|
BOOL CLongOperationDialog::LoadDescriptionString(UINT nID)
|
||
|
{
|
||
|
AFX_MANAGE_STATE(AfxGetStaticModuleState());
|
||
|
return m_strDescription.LoadString(nID);
|
||
|
}
|
||
|
|
||
|
BEGIN_MESSAGE_MAP(CLongOperationDialog, CDialog)
|
||
|
ON_MESSAGE( CLongOperationDialog::s_nNotificationMessage, OnNotificationMessage )
|
||
|
END_MESSAGE_MAP()
|
||
|
|
||
|
|
||
|
afx_msg LONG CLongOperationDialog::OnNotificationMessage( WPARAM wParam, LPARAM lParam)
|
||
|
{
|
||
|
TRACE(_T("CLongOperationDialog::OnNotificationMessage()\n"));
|
||
|
|
||
|
ASSERT(m_pThreadObj != NULL);
|
||
|
if (m_pThreadObj != NULL)
|
||
|
{
|
||
|
m_pThreadObj->AcknowledgeExiting();
|
||
|
VERIFY(WAIT_OBJECT_0 == ::WaitForSingleObject(m_pThreadObj->m_hThread,INFINITE));
|
||
|
m_bAbandoned = FALSE;
|
||
|
PostMessage(WM_CLOSE,0,0);
|
||
|
}
|
||
|
return 0;
|
||
|
}
|
||
|
|
||
|
BOOL CLongOperationDialog::OnInitDialog()
|
||
|
{
|
||
|
TRACE(_T("CLongOperationDialog::OnInitDialog()\n"));
|
||
|
|
||
|
CDialog::OnInitDialog();
|
||
|
|
||
|
if (!m_strTitle.IsEmpty())
|
||
|
SetWindowText(m_strTitle);
|
||
|
|
||
|
if (!m_strDescription.IsEmpty())
|
||
|
GetDlgItem(IDC_STATIC_DESCRIPTION)->SetWindowText(m_strDescription);
|
||
|
|
||
|
// load auto play AVI file if needed
|
||
|
if (m_nAviID != -1)
|
||
|
{
|
||
|
AFX_MANAGE_STATE(AfxGetStaticModuleState());
|
||
|
CAnimateCtrl* pAnimate = (CAnimateCtrl*)GetDlgItem(IDC_SEARCH_ANIMATE);
|
||
|
VERIFY(pAnimate->Open(m_nAviID));
|
||
|
}
|
||
|
|
||
|
if (!m_bCancel)
|
||
|
{
|
||
|
// hide the system menu
|
||
|
DWORD dwWindowStyle = GetWindowLong(GetSafeHwnd(), GWL_STYLE);
|
||
|
dwWindowStyle &= ~WS_SYSMENU;
|
||
|
|
||
|
SetWindowLong(GetSafeHwnd(), GWL_STYLE, dwWindowStyle);
|
||
|
|
||
|
// hide the cancel button
|
||
|
GetDlgItem(IDCANCEL)->ShowWindow(FALSE);
|
||
|
}
|
||
|
|
||
|
// spawn worker thread
|
||
|
GetThreadObj()->Start(this);
|
||
|
|
||
|
return TRUE;
|
||
|
}
|
||
|
|
||
|
void CLongOperationDialog::OnCancel()
|
||
|
{
|
||
|
TRACE(_T("CLongOperationDialog::OnCancel()\n"));
|
||
|
if (m_bAbandoned)
|
||
|
{
|
||
|
m_pThreadObj->Abandon();
|
||
|
m_pThreadObj = NULL;
|
||
|
}
|
||
|
CDialog::OnCancel();
|
||
|
}
|