// If you add a minimize button to your dialog, you will need the code below // to draw the icon. For MFC applications using the document/view model, // this is automatically done for you by the framework.
void CGetCodeDlg::OnPaint() { if (IsIconic()) { CPaintDC dc(this); // device context for painting
SendMessage(WM_ICONERASEBKGND, (WPARAM) dc.GetSafeHdc(), 0);
// Center icon in client rectangle int cxIcon = GetSystemMetrics(SM_CXICON); int cyIcon = GetSystemMetrics(SM_CYICON); CRect rect; GetClientRect(&rect); int x = (rect.Width() - cxIcon + 1) / 2; int y = (rect.Height() - cyIcon + 1) / 2;
// Draw the icon dc.DrawIcon(x, y, m_hIcon); } else { CDialog::OnPaint(); } }
// The system calls this to obtain the cursor to display while the user drags // the minimized window. HCURSOR CGetCodeDlg::OnQueryDragIcon() { return (HCURSOR) m_hIcon; } void CGetCodeDlg::OnOK() { //读取控件文本,并保存到文件 GetDlgItemText(IDC_EDIT1,lpszDialogCaption,80); GetDlgItemText(IDC_EDIT2,lpszButtonConfirmCaption,20); GetDlgItemText(IDC_EDIT3,lpszDialogRetryCaption,80); GetDlgItemText(IDC_EDIT4,lpszButtonRetryCaption,20); GetDlgItemText(IDC_EDIT5,lpszThreadCount,20); GetDlgItemText(IDC_EDIT6,lpszPath,MAX_PATH); nThreadCount=(int)GetDlgItemInt(IDC_EDIT5,NULL,true); if ((nThreadCount<1)||(nThreadCount>50)) {SetDlgItemText(IDC_EDIT5,"5"); GetDlgItem(IDC_EDIT5)->SetFocus(); return ; } WritePrivateProfileString("设置","线程计数",lpszThreadCount,"Setup.ini"); WritePrivateProfileString("设置","口令输入窗口标题",lpszDialogCaption,"Setup.ini"); WritePrivateProfileString("设置","口令输入窗口确认按钮标题",lpszButtonConfirmCaption,"Setup.ini"); WritePrivateProfileString("设置","提示口令错要求重新输入窗口标题",lpszDialogRetryCaption,"Setup.ini"); WritePrivateProfileString("设置","提示口令错要求重新输入窗口确认按钮标题",lpszButtonRetryCaption,"Setup.ini"); WritePrivateProfileString("设置","穷举文件",lpszPath,"Setup.ini"); LPTSTR lpszTemp; if(this->GetCheckedRadioButton(IDC_RADIO1,IDC_RADIO7)==IDC_RADIO1)lpszTemp="数字"; if(this->GetCheckedRadioButton(IDC_RADIO1,IDC_RADIO7)==IDC_RADIO2)lpszTemp="小写字母"; if(this->GetCheckedRadioButton(IDC_RADIO1,IDC_RADIO7)==IDC_RADIO3)lpszTemp="大写字母"; if(this->GetCheckedRadioButton(IDC_RADIO1,IDC_RADIO7)==IDC_RADIO4)lpszTemp="大小写字母组合"; if(this->GetCheckedRadioButton(IDC_RADIO1,IDC_RADIO7)==IDC_RADIO5)lpszTemp="数字字母组合"; if(this->GetCheckedRadioButton(IDC_RADIO1,IDC_RADIO7)==IDC_RADIO6)lpszTemp="所有字符"; if(this->GetCheckedRadioButton(IDC_RADIO1,IDC_RADIO7)==IDC_RADIO7)lpszTemp="数据字典"; WritePrivateProfileString("设置","穷举方法",lpszTemp,"Setup.ini"); //按钮互锁 m_OK.EnableWindow(FALSE); m_Quit.EnableWindow(FALSE); m_Pause.EnableWindow(TRUE); m_Pause.SetFocus(); //对话框最小化 this->PostMessage(WM_SYSCOMMAND,SC_MINIMIZE,0); //如果对话框尚未创建线程,创建线程,且允许线程运行结束自动销毁 if (m_pEnumThread[0].pThread ==NULL) { UINT i; for(i=1;i<=this->m_nThreadCount ;i++) {//优先级最低可以相应的提高密码应用程序的对话框响应速度 m_pEnumThread[i].pThread=AfxBeginThread((AFX_THREADPROC)EnumProc,(LPVOID)0,THREAD_PRIORITY_LOWEST,0,0,NULL); m_pEnumThread[i].pThread->m_bAutoDelete =true; } } else //如果线程已经创建,唤醒挂起的线程 { UINT i; for(i=1;i<=this->m_nThreadCount;i++) m_pEnumThread[i].pThread->ResumeThread(); } } DWORD WINAPI EnumProc( LPVOID ) {//通过布尔变量m_bEnum 实现循环枚举窗口,若 m_bEnum 为假,线程退出自动销毁 while (m_bEnum) { ::EnumWindows((WNDENUMPROC)EnumWindowsProc,NULL); } return true; } BOOL CALLBACK EnumWindowsProc(HWND hwnd,LPARAM lParam ) { if (!IsWindowVisible(hwnd)) return true;//当窗口不可见时,接着枚举下一窗口 char lpString[128]="\0";
::GetWindowText(hwnd,(LPSTR)lpString,sizeof(lpString)); //通过窗口标题查找所需窗口 if(strstr(lpString,(const char *)lpszDialogCaption)!=NULL) {//第一发现所需窗口的线程,获得互斥信号量,其它线程被阻住 ::WaitForSingleObject(m_hMutex,INFINITE); //枚举父窗口下的子窗口 ::EnumChildWindows(hwnd,(WNDENUMPROC) EnumChildProc,INPUTDIALOGID); //线程执行完毕释放信号量,以便另外线程进入 ::ReleaseMutex(m_hMutex); return false;//返回假,枚举过程不再进行 } if(strstr(lpString,(const char *)lpszDialogRetryCaption)!=NULL) {::WaitForSingleObject(m_hMutex,INFINITE); ::EnumChildWindows(hwnd,(WNDENUMPROC) EnumChildProc,INPUTRETRYDIALOGID); ::ReleaseMutex(m_hMutex); return false; }
return true;非所需窗口,继续枚举 } BOOL CALLBACK EnumChildProc(HWND hwnd, LPARAM lParam) { if (!IsWindowVisible(hwnd)) return true;//子窗口不可见继续枚举下一子窗口 char szTemp[128]="\0"; DWORD dwStyle; switch((long)lParam) {case INPUTDIALOGID: if(!m_bPasswordStyle) {//尚未找到密码编辑框进入 dwStyle=(DWORD)GetWindowLong(hwnd,GWL_STYLE); if((dwStyle & ES_PASSWORD)== ES_PASSWORD) { //是密码编辑框 //枚举新密码,保存到公共变量lpszPassword中 EnumPasswordString(); ::SendDlgItemMessage(::GetParent(hwnd),GetWindowLong(hwnd,GWL_ID),WM_SETTEXT,0,(LPARAM)(LPCTSTR)lpszPassword); m_bPasswordStyle=true;//置密码编辑框发现标志 if (hButton1!=NULL)//若已经发现确定按钮,发送消息 //复位各个变量,返回false 停止枚举 {::SendMessage(::GetParent(hButton1),WM_COMMAND,(WPARAM)::GetWindowLong(hButton1,GWL_ID),(LPARAM)hButton1);
bFetched=true; hButton1=NULL; m_bPasswordStyle=false; return false; } return true;//还未发现确定按钮,继续枚举子窗口 } } if(hButton1==NULL) {//通过子窗口标题寻找指定按钮 ::GetWindowText(hwnd,(LPSTR) szTemp,sizeof(szTemp)); if(strstr(szTemp,(const char *)lpszButtonConfirmCaption)!=NULL) {hButton1=hwnd; if (m_bPasswordStyle)//若已经找到密码编辑框,发送键盘鼠标消息,//复位系统变量,退出枚举过程 {::SendMessage(::GetParent(hButton1),WM_COMMAND,(WPARAM)::GetWindowLong(hButton1,GWL_ID),(LPARAM)hButton1);
bFetched=true; hButton1=NULL; m_bPasswordStyle=false; return false; } return true;//未找到密码编辑框继续枚举 } return true;不是确定按钮,继续枚举 } return true; break; case INPUTRETRYDIALOGID: ::GetWindowText(hwnd,(LPSTR) szTemp,sizeof(szTemp)); if(strstr(szTemp,(const char *)lpszButtonRetryCaption)!=NULL) {hButton2=hwnd; ::SendMessage(::GetParent(hButton2),WM_COMMAND,(WPARAM)GetWindowLong(hButton2,GWL_ID),(LPARAM)hButton2); hButton2=NULL; return false; } return true; break; default:return true; } return false; }
void CGetCodeDlg::OnCANCEL() { m_bEnum=FALSE;//销毁线程
CDialog::OnCancel(); // TODO: Add your control notification handler code here
}
void CGetCodeDlg::OnPause() { //暂停枚举线程挂起
UINT i; for(i=1;i<=this->m_nThreadCount;i++) {m_pEnumThread[i].pThread->SuspendThread (); } //按钮联动 m_Pause.EnableWindow(FALSE); m_OK.EnableWindow(TRUE); m_Quit.EnableWindow(TRUE); m_OK.SetFocus(); } |