zoukankan      html  css  js  c++  java
  • Visual KB 《MFC Windows程序设计示例》

    //filename:VisualKB.h
    
    #define MAX_STRING 12
    
    class CMyApp:public CWinApp{
    public:
    	virtual BOOL InitInstance();
    };
    
    
    class CMainWindow:public CWnd
    {
    
    protected:
    	int m_cxChar;				//Average character width
    	int m_cyChar;				//Character height
    	int m_cyLine;				//Vertical line spacing in message box
    	int m_nTextPos;				//Index of current character for tabbed output
    	int m_nTabStops[7];			//Tab stop locations for tabbed output
    	int m_nTextLimit;			//Maximum width of text in text box
    	int m_nMsgPos;				//Current position in m_strMessages array
    
    	HCURSOR m_hCursorArrow;		//Handle of arrow cursor
    	HCURSOR m_hCursorIBeam;		//Handle of I-Beam cursor
    
    	CPoint m_ptTextOrigin;		//Origin for drawing input text
    	CPoint m_ptHeaderOrigin;	//Origin for drawing header text
    	CPoint m_ptUpperMsgOrigin;	//Origin of first line in message box
    	CPoint m_ptLowerMsgOrigin;	//Origin of first line in message box
    	CPoint m_ptCaretPos;		//Current caret position
    
    	CRect m_rcTextBox;			//Coordinates of text box
    	CRect m_rcTextBoxBorder;	//Coordinates of text box border
    	CRect m_rcMsgBoxBorder;		//Coordinates of message box border
    	CRect m_rcScroll;			//Coordinates of scroll rectangle
    
    	CString m_strInputText;						//Input text
    	CString m_stringMessages[MAX_STRING];		//Array Of message strings
    
    public:
    	CMainWindow();
    protected:
    	int GetNearestPos(CPoint point);
    	void PositionCaret(CDC * pDC=NULL);
    	void DrawInputText(CDC * pDC);
    	void ShowMessage(LPCTSTR pszMessage,UINT nChar,UINT nRepCnt,
    		UINT nFlags);
    	void DrawMessageHeader(CDC * pDC);
    	void DrawMessage(CDC * pDC);
    	void DrawMessages(CDC * pDC);
    protected:
    	virtual void PostNcDestroy();
    
    	afx_msg int  OnCreate(LPCREATESTRUCT lpCreateStruct);
    	afx_msg void OnPaint ();
    	afx_msg void OnSetFocus(CWnd* pWnd);	//old wnd
    	afx_msg void OnKillFocus(CWnd* pWnd);	//new wnd
    	afx_msg BOOL OnSetCursor(CWnd *pWnd,UINT nHitTest,UINT message);
    	afx_msg void OnLButtonDown(UINT nFlags, CPoint point);
    	afx_msg void OnKeyDown(UINT nChar, UINT nRepCnt, UINT nFlags);
    	afx_msg void OnKeyUp(UINT nChar, UINT nRepCnt, UINT nFlags);
    	afx_msg void OnSysKeyDown(UINT nChar, UINT nRepCnt, UINT nFlags);
    	afx_msg void OnSysKeyUp(UINT nChar, UINT nRepCnt, UINT nFlags);
    	afx_msg void OnChar(UINT nChar, UINT nRepCnt, UINT nFlags);
    	afx_msg void OnSysChar(UINT nChar, UINT nRepCnt, UINT nFlags);
    
    	DECLARE_MESSAGE_MAP()
    };
    
    //filename:VisualKB.cpp
    
    #include <afxwin.h>
    #include "VisualKB.h"
    
    CMyApp myApp;
    
    //CMyApp member functions
    
    BOOL CMyApp ::InitInstance()
    {
    	m_pMainWnd = new CMainWindow;
    	m_pMainWnd ->ShowWindow(m_nCmdShow);
    	m_pMainWnd->UpdateWindow();
    	return TRUE;
    }
    
    /////////////////////////////////////////////////////////
    //CMainWindow message map and number functiosn
    
    BEGIN_MESSAGE_MAP(CMainWindow,CWnd)
    	ON_WM_CREATE()
    	ON_WM_PAINT()
    	ON_WM_SETFOCUS()
    	ON_WM_SETFOCUS()
    	ON_WM_KILLFOCUS()
    	ON_WM_SETCURSOR()
    	ON_WM_LBUTTONDOWN()
    	ON_WM_KEYDOWN()
    	ON_WM_KEYUP()
    	ON_WM_SYSKEYDOWN()
    	ON_WM_SYSKEYUP()
    	ON_WM_CHAR()
    	ON_WM_SYSCHAR()
    END_MESSAGE_MAP()
    
    
    CMainWindow::CMainWindow()
    {
    	m_nTextPos = 0;
    	m_nMsgPos = 0;
    
    	m_hCursorArrow = AfxGetApp()->LoadStandardCursor(IDC_ARROW);
    	m_hCursorIBeam = AfxGetApp()->LoadStandardCursor(IDC_IBEAM);
    
    	//register a WNDCLASS
    	CString strWndClass = AfxRegisterWndClass(
    		0,
    		NULL,
    		(HBRUSH)(COLOR_3DFACE + 1),
    		AfxGetApp()->LoadStandardIcon(IDI_WINLOGO)
    	);
    	
    	//create a window
    	CreateEx(0,strWndClass,_T("Visual Keyboard"),
    		WS_OVERLAPPED | WS_SYSMENU | WS_CAPTION | WS_MINIMIZEBOX,
    		CW_USEDEFAULT,CW_USEDEFAULT,CW_USEDEFAULT,CW_USEDEFAULT,
    		NULL,NULL
    		);
    }
    
    
    int CMainWindow::OnCreate(LPCREATESTRUCT lpCreateStruct)
    {
    	if(CWnd::OnCreate(lpCreateStruct)==-1)
    	{
    		return -1;
    	}
    	CClientDC dc(this);
    	TEXTMETRIC tm;
    	dc.GetTextMetrics(&tm);
    	m_cxChar = tm.tmAveCharWidth;
    	m_cyChar = tm.tmHeight;
    	m_cyLine = tm.tmHeight + tm.tmExternalLeading;
    
    	m_rcTextBoxBorder.SetRect(16,16,(m_cxChar*64)+16,
    		((m_cyChar*3)/2)+16
    	);
    	m_rcTextBox = m_rcTextBoxBorder;
    	m_rcTextBox.InflateRect(-2,-2);
    
    	m_rcMsgBoxBorder.SetRect(16, (m_cyChar*4)+16,
    		(m_cxChar * 64)+16,(m_cyLine * MAX_STRING)+(m_cyChar * 6)+16
    		);
    	m_rcScroll.SetRect(m_cxChar + 16,(m_cyChar * 4)+16,
    		(m_cxChar * 64)+16, (m_cyLine * MAX_STRING )
    		+ (m_cyChar * 6) + 16
    		);
    	m_ptTextOrigin.x = m_cxChar + 16;
    	m_ptTextOrigin.y = (m_cyChar /4 )+16;
    	m_ptCaretPos = m_ptTextOrigin;
    	m_nTextLimit = (m_cxChar * 63)+16;
    
    	m_ptHeaderOrigin.x = m_cxChar + 16;
    	m_ptHeaderOrigin.y = (m_cyChar * 3)+16;
    
    	m_ptUpperMsgOrigin.x = m_cxChar + 16;
    	m_ptUpperMsgOrigin.y = m_cyChar * 5 + 16;
    
    	m_ptLowerMsgOrigin.x = m_cxChar + 16;
    	m_ptLowerMsgOrigin.y = (m_cyChar * 5)
    		+ m_cyLine * (MAX_STRING -1)+16;
    
    	m_nTabStops[0] = (m_cxChar * 24) + 16;
    	m_nTabStops[1] = (m_cxChar * 30) + 16;
    	m_nTabStops[2] = (m_cxChar * 36) + 16;
    	m_nTabStops[3] = (m_cxChar * 42) + 16;
    	m_nTabStops[4] = (m_cxChar * 46) + 16;
    	m_nTabStops[5] = (m_cxChar * 50) + 16;
    	m_nTabStops[6] = (m_cxChar * 54) + 16;
    
    	CRect rect(0,0,m_rcMsgBoxBorder.right + 16,
    		m_rcMsgBoxBorder.bottom + 16);
    	CalcWindowRect(&rect);
    	SetWindowPos(NULL,0,0,rect.Width() ,rect.Height(),
    		SWP_NOZORDER | SWP_NOMOVE | SWP_NOREDRAW);
    	return 0;
    }
    
    void CMainWindow::PostNcDestroy()
    {
    	delete this;
    }
    
    void CMainWindow::OnPaint()
    {
    	CPaintDC dc(this);
    
    	dc.DrawEdge(m_rcTextBoxBorder,EDGE_SUNKEN,BF_RECT);
    	dc.DrawEdge(m_rcMsgBoxBorder,EDGE_SUNKEN,BF_RECT);
    
    	DrawInputText(&dc);
    	DrawMessageHeader(&dc);
    	DrawMessage(&dc);
    }
    
    void CMainWindow::OnSetFocus(CWnd* pWnd){
    	CreateSolidCaret(max(2,::GetSystemMetrics(SM_CXBORDER)),
    		m_cyChar);
    	SetCaretPos(m_ptCaretPos);
    	ShowCaret();
    }
    
    void CMainWindow::OnKillFocus(CWnd* pWnd){
    	HideCaret();
    	m_ptCaretPos = GetCaretPos();
    	::DestroyCaret();
    }
    
    BOOL CMainWindow::OnSetCursor(CWnd *pWnd,UINT nHitTest,UINT message)
    {
    	if(nHitTest == HTCLIENT)
    	{
    		DWORD dwPos = ::GetMessagePos();
    		CPoint point(LOWORD(dwPos),HIWORD(dwPos));
    		ScreenToClient(&point);
    		::SetCursor(m_rcTextBox.PtInRect(point)?
    				m_hCursorIBeam:m_hCursorArrow);
    		return TRUE;
    	}
    	return CWnd::OnSetCursor(pWnd,nHitTest,message);
    }
    
    void CMainWindow::OnLButtonDown(UINT nFlags, CPoint point)
    {
    	if(m_rcTextBox.PtInRect(point))
    	{
    		m_nTextPos = GetNearestPos(point);
    		PositionCaret();
    	}
    }
    
    void CMainWindow::OnKeyDown(UINT nChar, UINT nRepCnt, UINT nFlags)
    {
    	ShowMessage(_T("WM_KEYDOWN"),nChar,nRepCnt,nFlags);
    
    	switch (nChar)
    	{
    	case VK_LEFT:
    		if(m_nTextPos !=0){
    			m_nTextPos --;
    			PositionCaret();
    		}
    		break;
    	case VK_RIGHT:
    		if(m_nTextPos != m_strInputText.GetLength())
    		{
    			m_nTextPos++;
    			PositionCaret();
    		}
    		break;
    	case VK_HOME:
    		m_nTextPos = 0;
    		PositionCaret();
    		break;
    	case VK_END:
    		m_nTextPos = m_strInputText.GetLength();
    		PositionCaret();
    		break;
    	}
    }
    
    void CMainWindow::OnChar(UINT nChar, UINT nRepCnt, UINT nFlags)
    {
    	ShowMessage(_T("WM_CHAR"),nChar,nRepCnt,nFlags);
    	CClientDC dc(this);
    
    	switch (nChar)
    	{
    	case VK_ESCAPE:
    	case VK_RETURN:
    		m_strInputText.Empty();
    		m_nTextPos = 0;
    		break;
    	case VK_BACK:
    		if(m_nTextPos != 0)
    		{
    			m_strInputText = m_strInputText.Left(m_nTextPos-1)
    				+m_strInputText.Right(m_strInputText.GetLength()
    				- m_nTextPos);
    			m_nTextPos--;
    		}
    		break;
    	default:
    		if((nChar>=0) && (nChar <= 31))
    			return;
    		if(m_nTextPos == m_strInputText.GetLength())
    		{
    			m_strInputText += nChar;
    			m_nTextPos ++;
    		}
    		else 
    			m_strInputText.SetAt(m_nTextPos++,nChar);
    
    		CSize size = dc.GetTextExtent(m_strInputText,
    			m_strInputText.GetLength());
    		if((m_ptTextOrigin.x + size.cx) > m_nTextLimit)
    		{
    			m_strInputText = nChar;
    			m_nTextPos = 1;
    		}
    		break;
    	}
    
    	HideCaret();
    	DrawInputText(&dc);
    	PositionCaret(&dc);
    	ShowCaret();
    }
    
    void CMainWindow::OnKeyUp(UINT nChar, UINT nRepCnt, UINT nFlags)
    {
    	ShowMessage(_T("WM_KEYUP"),nChar,nRepCnt,nFlags);
    	CWnd::OnKeyUp(nChar,nRepCnt,nFlags);
    }
    
    void CMainWindow::OnSysKeyDown(UINT nChar, UINT nRepCnt, UINT nFlags)
    {
    	ShowMessage(_T("WM_SYSKEYDOWN"),nChar,nRepCnt,nFlags);
    	CWnd::OnSysKeyDown(nChar,nRepCnt,nFlags);
    }
    void CMainWindow::OnSysChar(UINT nChar, UINT nRepCnt, UINT nFlags)
    {
    	ShowMessage(_T("WM_SYSCHAR"),nChar,nRepCnt,nFlags);
    	CWnd::OnSysChar(nChar,nRepCnt,nFlags);
    }
    void CMainWindow::OnSysKeyUp(UINT nChar, UINT nRepCnt, UINT nFlags)
    {
    	ShowMessage(_T("WM_SYSKEYUP"),nChar,nRepCnt,nFlags);
    	CWnd::OnSysKeyUp(nChar,nRepCnt,nFlags);
    }
    
    void CMainWindow :: PositionCaret(CDC * pDC/* =NULL */)
    {
    	BOOL bRelease = FALSE;
    	if(pDC == NULL){
    		pDC = GetDC();
    		bRelease = true;
    	}
    
    	CPoint point = m_ptTextOrigin;	
    	CString string = m_strInputText.Left(m_nTextPos);
    	point.x += (pDC ->GetTextExtent(string,string.GetLength())).cx;
    	SetCaretPos(point);
    
    	if(bRelease) ReleaseDC(pDC);
    }
    
    int CMainWindow::GetNearestPos(CPoint point)
    {
    	if(point.x  <= m_ptTextOrigin.x) return 0;
    
    	CClientDC dc(this);
    	int nLen = m_strInputText.GetLength();
    	if(point.x >= (m_ptTextOrigin.x+dc.GetTextExtent(m_strInputText,nLen).cx)) return nLen;
    	
    	int i=0;
    	int nPrevChar = m_ptTextOrigin.x;
    	int nNextChar = m_ptTextOrigin.x;
    	while(nNextChar < point.x){
    		i++;
    		nPrevChar = nNextChar;
    		nNextChar = m_ptTextOrigin.x + 
    			dc.GetTextExtent(m_strInputText.Left(i),i).cx;
    
    	}
    	return point.x - nPrevChar < nNextChar - point.x ? i-1 : i ;
    }
    
    
    void CMainWindow::DrawInputText(CDC * pDC)
    {
    	pDC ->ExtTextOut(m_ptTextOrigin.x,m_ptTextOrigin.y,
    		ETO_OPAQUE,m_rcTextBox,m_strInputText,NULL);
    }
    
    void CMainWindow::ShowMessage(LPCTSTR pszMessage,UINT nChar,UINT nRepCnt, UINT nFlags)
    {
    	CString string;
    	string.Format(_T("%s\t %u\t %u\t %u\t %u\t %u\t %u\t %u"),
    		pszMessage,nChar,nRepCnt,nFlags & 0xFF,
    		(nFlags >> 8 ) & 0x01,
    		(nFlags >> 13) & 0x01,
    		(nFlags >> 14) & 0x01,
    		(nFlags >> 15) & 0x01
    		);
    
    	ScrollWindow(0,-m_cyLine,&m_rcScroll);
    	ValidateRect(m_rcScroll);
    
    	CClientDC dc(this);
    	dc.SetBkColor((COLORREF)::GetSysColor(COLOR_3DFACE));
    	m_stringMessages[m_nMsgPos] = string;
    	dc.TabbedTextOut(m_ptLowerMsgOrigin.x,m_ptLowerMsgOrigin.y,
    		m_stringMessages[m_nMsgPos],m_stringMessages[m_nMsgPos].GetLength(),
    		sizeof(m_nTabStops),m_nTabStops , m_ptLowerMsgOrigin.x);
    
    	if(++m_nMsgPos == MAX_STRING) m_nMsgPos = 0;
    }
    
    void CMainWindow ::DrawMessageHeader(CDC * pDC)
    {
    	static CString string = _T("Message\tChar\tRep\tScan\tExt\tCan\tPrv\tTran");
    	pDC->SetBkColor((COLORREF)::GetSysColor(COLOR_3DFACE));
    	pDC->TabbedTextOut(m_ptHeaderOrigin.x,m_ptHeaderOrigin.y,
    		string,string.GetLength(),sizeof(m_nTabStops),m_nTabStops,m_ptHeaderOrigin.x);
    }
    
    void CMainWindow::DrawMessage(CDC * pDC)
    {
    	int nPos = m_nMsgPos;
    	pDC->SetBkColor((COLORREF)::GetSysColor(COLOR_3DFACE));
    	for(int i=0;i<MAX_STRING;i++){
    		pDC->TabbedTextOut(m_ptUpperMsgOrigin.x,
    			m_ptUpperMsgOrigin.y + m_cyLine*i,
    			m_stringMessages[nPos],
    			m_stringMessages[nPos].GetLength(),
    			sizeof(m_nTabStops),m_nTabStops,m_ptUpperMsgOrigin.x);
    		if(++nPos == MAX_STRING) nPos = 0;
    	}
    }
    
    
  • 相关阅读:
    第二十一章流 1流的操作 简单
    第二十章友元类与嵌套类 1友元类 简单
    第十九章 19 利用私有继承来实现代码重用 简单
    第二十章友元类与嵌套类 2嵌套类 简单
    第十九章 8链表类Node 简单
    第二十一章流 3用cin输入 简单
    第十九章 10 图书 药品管理系统 简单
    第十九章 11图书 药品管理系统 简单
    第二十一章流 4文件的输入和输出 简单
    第十九章 12 什么时候使用私有继承,什么时候使用包含 简单
  • 原文地址:https://www.cnblogs.com/wucg/p/2377175.html
Copyright © 2011-2022 走看看