附录3:可供两个人对弈的中国象棋程序 350- 附录3:可供两人对弈的中国象棋程序 / Sample10-4:中国象棋程序 #include SelectObject(&penRed2) for(int i<10;i+)
附录 3:可供两个人对弈的中国象棋程序 - 350 - 附录 3:可供两人对弈的中国象棋程序 // Sample 10-4: 中国象棋程序 #include // 棋盘类 class CPlate { int m_ndx; // 棋盘格宽 int m_ndy; // 棋盘格高 int m_nLeft; // 棋盘位置 int m_nTop; int m_nRight; int m_nBottom; public: CPlate(); void ShowPlate(CDC *pDC); void DrawConer(CDC *pDC, int row, int col, int type); CPoint GetPosition(int col, int row); }; // 棋盘类的成员函数 // 构造函数: 初始化 CPlate::CPlate() { m_ndx = 50; m_ndy = 45; m_nLeft = 198; m_nTop = 30; m_nRight = m_nLeft+m_ndx*8; m_nBottom = m_nTop+m_ndy*9; } // 显示棋盘 void CPlate::ShowPlate(CDC *pDC) { // 画棋盘方格 CPen penRed2(PS_SOLID,2,RGB(255,0,0)); CPen *pOldPen = pDC->SelectObject(&penRed2); for(int i=0; i<10; i++)
附录3:可供两个人对弈的中国象棋程序 351 pDC->Move To(m nLeft, m nTop+ pDC->LineTo(m nIght, m nTop+i*m ndy) for(i if(i==0|i==8) pDC->Move To(m nLeft+i*m ndx, m nTop) pDC->Line To(m nLeft+i*km ndx, m nBot tom pDC->Move To(m nLeft+i=sm ndx, m nTop pDC->Line To(m nLeft+i=lm ndx, m nTop+4*m ndy) pDC->Move To(m nLeft+i*km ndx, m nTop+5*m ndy) pDC->Line To(m nLeft+i=*m ndx, m nBot tom) /画棋盘斜线 pDC->SelectObject(pOldPen) CPen penRed1(PS SOLID, 1, RGB(255, 0, 0)) pOldPen pDC->SelectObject(&penRed1) pDC->Move To(m nLeft+3*m ndx, m nTop) DC->LineTo(m nLeft+5*m ndx, m nTop+2*m ndy) pDC->MoveTo(m nLeft+3*m ndx, m nTop+2*m ndy) pDC->LineTo(m nLeft+5*m ndx, m nTop pDC->MoveTo(m nLeft+3*m ndx, m nBottom pDC->Line To(m nLeft+5*m ndx, m nBottom-2*m ndy) pDC->MoveTo(m nLeft+3*m ndx, m nBottom-2*m ndy) DC->LineTo(m nLeft+5*m ndx, m bOttom) pDC->SelectObject(poldPen) /画兵,炮位标记 DrawConer(pDC, 2, 1, 0) DrawConer (pDC, 2, 7, 0) DrawConer (pDC, 3, 0, 1) DrawConer (pDC, 3, 2, 0) DrawConer (pDC, 3, 4, 0) (pDC,3,6,0)
附录 3:可供两个人对弈的中国象棋程序 - 351 - { pDC->MoveTo(m_nLeft, m_nTop+i*m_ndy); pDC->LineTo(m_nRight, m_nTop+i*m_ndy); } for(i=0; iMoveTo(m_nLeft+i*m_ndx, m_nTop); pDC->LineTo(m_nLeft+i*m_ndx, m_nBottom); } else{ pDC->MoveTo(m_nLeft+i*m_ndx, m_nTop); pDC->LineTo(m_nLeft+i*m_ndx, m_nTop+4*m_ndy); pDC->MoveTo(m_nLeft+i*m_ndx, m_nTop+5*m_ndy); pDC->LineTo(m_nLeft+i*m_ndx, m_nBottom); } } // 画棋盘斜线 pDC->SelectObject(pOldPen); CPen penRed1(PS_SOLID,1,RGB(255,0,0)); pOldPen = pDC->SelectObject(&penRed1); pDC->MoveTo(m_nLeft+3*m_ndx, m_nTop); pDC->LineTo(m_nLeft+5*m_ndx, m_nTop+2*m_ndy); pDC->MoveTo(m_nLeft+3*m_ndx, m_nTop+2*m_ndy); pDC->LineTo(m_nLeft+5*m_ndx, m_nTop); pDC->MoveTo(m_nLeft+3*m_ndx, m_nBottom); pDC->LineTo(m_nLeft+5*m_ndx, m_nBottom-2*m_ndy); pDC->MoveTo(m_nLeft+3*m_ndx, m_nBottom-2*m_ndy); pDC->LineTo(m_nLeft+5*m_ndx, m_nBottom); pDC->SelectObject(pOldPen); // 画兵, 炮位标记 DrawConer(pDC, 2, 1, 0); DrawConer(pDC, 2, 7, 0); DrawConer(pDC, 3, 0, 1); DrawConer(pDC, 3, 2, 0); DrawConer(pDC, 3, 4, 0); DrawConer(pDC, 3, 6, 0);
附录3:可供两个人对弈的中国象棋程序 352 DrawConer (pDC, 3, 8, 2) DrawConer (pDC, 7, 1, 0) DrawConer (pDC, 7, 7, 0) DrawConer(pDC, 6, 0, 1) DrawConer(pDC, 6, 2, 0) DrawConer(pDC, 6, 4, 0) DrawConer(pDC, 6, 6, 0) /绘制兵,炮位标志 void CPlate: DrawConer(CDC *pDC, int row, int col, int type CPen penRed1(PS SOLID, 1, RGB(255, 0, 0)) CPen *pOldPen pDC->SelectObject(&penRed1) if(type =0 II type = 1) pDC->Move To(m nLeft+col*m ndx+3, m nToptrow*m ndy-10 pDC->LineTo(m nLeft+col=*m ndx+ 3, m n Toptrowkm ndy-3) pDC->LineTo(m nLeft+col*km ndx+10, m n Toptrowsm ndy-3) pDC->Move To(m nLeft+col*m ndx+3, m nToptrow*km ndy+10) neTo(m nLeft+col=*m ndx+ 3, m nTop+ pDC->LineTo(m nLeft+col*m ndx+10, m nToptrowkm ndy+3) pDC->MoveTo(m nLeft+col*m ndx-3, m n Toptrowkm ndy-10) pDC->Line To(m nLeft+col*m ndx- 3, m n Toptrow*m ndy-3) pDC->LineTo(m nLeft+col=*m ndx-10, m n Toptrowakm ndy-3) pDC->Line To(m nLeft+col *km ndx-3, m nToptrow*m ndy+3) pDC->LineTo(m nLeft+col=m ndx-10, m n Toptrowkm ndy+3) pDC->SelectObject(pOldPen) /取棋盘上各交叉点的坐标 CPoint CPlate: GetPosition (int col, int row)
附录 3:可供两个人对弈的中国象棋程序 - 352 - DrawConer(pDC, 3, 8, 2); DrawConer(pDC, 7, 1, 0); DrawConer(pDC, 7, 7, 0); DrawConer(pDC, 6, 0, 1); DrawConer(pDC, 6, 2, 0); DrawConer(pDC, 6, 4, 0); DrawConer(pDC, 6, 6, 0); DrawConer(pDC, 6, 8, 2); } // 绘制兵, 炮位标志 void CPlate::DrawConer(CDC *pDC, int row, int col, int type) { CPen penRed1(PS_SOLID,1,RGB(255,0,0)); CPen *pOldPen = pDC->SelectObject(&penRed1); if(type == 0 || type == 1) { pDC->MoveTo(m_nLeft+col*m_ndx+ 3, m_nTop+row*m_ndy-10); pDC->LineTo(m_nLeft+col*m_ndx+ 3, m_nTop+row*m_ndy-3); pDC->LineTo(m_nLeft+col*m_ndx+10, m_nTop+row*m_ndy-3); pDC->MoveTo(m_nLeft+col*m_ndx+ 3, m_nTop+row*m_ndy+10); pDC->LineTo(m_nLeft+col*m_ndx+ 3, m_nTop+row*m_ndy+3); pDC->LineTo(m_nLeft+col*m_ndx+10, m_nTop+row*m_ndy+3); } if(type == 0 || type == 2) { pDC->MoveTo(m_nLeft+col*m_ndx- 3, m_nTop+row*m_ndy-10); pDC->LineTo(m_nLeft+col*m_ndx- 3, m_nTop+row*m_ndy-3); pDC->LineTo(m_nLeft+col*m_ndx-10, m_nTop+row*m_ndy-3); pDC->MoveTo(m_nLeft+col*m_ndx- 3, m_nTop+row*m_ndy+10); pDC->LineTo(m_nLeft+col*m_ndx- 3, m_nTop+row*m_ndy+3); pDC->LineTo(m_nLeft+col*m_ndx-10, m_nTop+row*m_ndy+3); } pDC->SelectObject(pOldPen); } // 取棋盘上各交叉点的坐标 CPoint CPlate::GetPosition(int col, int row) { CPoint point;
附录3:可供两个人对弈的中国象棋程序 353- point x =m nLeft+col*m ndx point. y m nToptrowakm ndy /棋子类 //定义棋子名称 #define BING 1 #define PAO 2 efine JU #define #define XIANG 5 #define SHII 6 #define JIANG 7 class stone BOOL /是否红方 booL m sElected;//是否被选择 m /路 m nrow CRect m rectstone;∥/棋子包含矩形 BOOI /是否显示 CString m sName /棋子名称 m nR: /棋子半径 m nType /棋子类型 lbl STone o什} CStone (BOOL red, int col, int row, LPCSTR name, int type, CPlate &plate) void ShowStone(CDC *pDC) d Move To (int col, int row, CPlate &plate) CRect GetRecto freturn m rectStone: I GetType ireturn m nType: 1 BOOL BeKilled (int col, int row) freturn m bShow & m nCol==col & m nRow = row BOOLMouseOnStone(CPoint point) [return m rectStone. PtInRect(point)&& m bShow: I voidKillItoim bShow FALSE: I voidSelectStone o(m sElected =!m bSelected; 1
附录 3:可供两个人对弈的中国象棋程序 - 353 - point.x = m_nLeft+col*m_ndx; point.y = m_nTop+row*m_ndy; return point; } // 棋子类 // 定义棋子名称 #define BING 1 #define PAO 2 #define JU 3 #define MA 4 #define XIANG 5 #define SHI 6 #define JIANG 7 class CStone { BOOL m_bRed; // 是否红方 BOOL m_bSelected; // 是否被选择 int m_nCol; // 路 int m_nRow; // 行 CRect m_rectStone; // 棋子包含矩形 BOOL m_bShow; // 是否显示 CString m_sName; // 棋子名称 int m_nR; // 棋子半径 int m_nType; // 棋子类型 public: CStone (){} CStone (BOOL red, int col, int row, LPCSTR name, int type, CPlate &plate); void ShowStone(CDC *pDC); void MoveTo(int col, int row, CPlate &plate); CRect GetRect(){return m_rectStone;} int GetType(){return m_nType;} BOOL BeKilled(int col, int row) {return m_bShow && m_nCol==col && m_nRow == row;} BOOLMouseOnStone(CPoint point) {return m_rectStone.PtInRect(point) && m_bShow;} voidKillIt(){m_bShow = FALSE;} voidSelectStone(){m_bSelected = !m_bSelected;} };
附录3:可供两个人对弈的中国象棋程序 354 /棋子类的成员函数 /棋子类的构造函数:初始化棋子 CStone: CStone(BOoL red, int col, int row, LPCSTR name, int type, CPlate &plate) m show TRUE m sElected False: m nRow row m sName type CPoint pos plate GetPosition(col, row) m rectStone =CRect(pos x-m nR, pos y-m nR, pos x+m nR, pos. y+m nR) /显示棋子 id CStone: ShowStone(CDC *pDC) if( m show)//只有未被吃掉的棋子才显示 //准备画棋子的画笔和画刷 CPen * dPen, pen Normal (PS SOLID, 3, RGB(120, 120, 120)) CBrush *kpOldBrush, brushNormal, brushSelected brushNormal. CreateSolidBrush (RGB(255, 255, 0)) brushSelected. CreateSolidBrush(RGB(127, 127, 0)) pOldPen pDC->SelectOb ject(&pen Normal) //被选中的棋子颜色不同 if(m sElected) pOldBrush pDC->SelectOb ject(&brush Selected) else pOldBrush =pDC-SelectObject(&brushNormal) /显示棋子 CRect r(m rectStone) r. right pDC->Ellipse(r)
附录 3:可供两个人对弈的中国象棋程序 - 354 - // 棋子类的成员函数 // 棋子类的构造函数:初始化棋子 CStone::CStone(BOOL red, int col, int row, LPCSTR name, int type, CPlate &plate) { m_bShow = TRUE; m_bSelected = FALSE; m_bRed = red; m_nCol = col; m_nRow = row; m_sName = name; m_nType = type; m_nR = 23; CPoint pos = plate.GetPosition(col, row); m_rectStone = CRect(pos.x-m_nR, pos.y-m_nR, pos.x+m_nR, pos.y+m_nR); } // 显示棋子 void CStone::ShowStone(CDC *pDC) { if(m_bShow) // 只有未被吃掉的棋子才显示 { // 准备画棋子的画笔和画刷 CPen *pOldPen, penNormal(PS_SOLID, 3, RGB(120, 120, 120)); CBrush *pOldBrush, brushNormal, brushSelected; brushNormal.CreateSolidBrush(RGB(255, 255, 0)); brushSelected.CreateSolidBrush(RGB(127, 127, 0)); pOldPen = pDC->SelectObject(&penNormal); // 被选中的棋子颜色不同 if(m_bSelected) pOldBrush = pDC->SelectObject(&brushSelected); else pOldBrush = pDC->SelectObject(&brushNormal); // 显示棋子 CRect r(m_rectStone); r.left ++; r.top ++; r.right --; r.bottom--; pDC->Ellipse(r);
附录3:可供两个人对弈的中国象棋程序 355 pDC->SelectObject(pOldPen) pDC->SelectObject(poldBrush): //准备显示棋子名称的字体 CFont *kpOIdFont, footStone fontStone. CreateFont(40, 0, 0, 0, 400, FALSE, FALSE 0. OEM CHARSET. OUT DEFAULT PRECIS CLIP DEFAULT PRECIS, DEFAULT QUALITY, DEFAULT PITCH,"楷体") pOldFont pDC->SelectObject(&fontStone int tx m rectStone, left+e int ty = m rectStone. top+6 pDC->Set BkMode(TRANSparENT) /棋子背景均为黄色,字分红、黑两色 pDC->Set TextColor(RGB(m bRed? 255: 0, 0, 0)) pDC->TextOut(tx, ty, m sName) pDC->SelectObject(poldFont) //将棋子放到指定位置 void CStone:: Move To(int col, int row, CPlate &plate) m sElected FAlse row olate GetPosition(col, row) m rectStone= CRect(pos x-m nR, pos y-m nR, pos x+m nR, pos. y+m nR) /框架窗口类 class CMy Wnd: public CFrameWnd CPlate m plate //棋盘 STone m stonelist[32];//棋子数组 booL m bRedTurn /轮红方下 booL m sElect one /已选择一棋子 int m nWhichStone ′被选择棋子的编号 CRect m rect Info /信息显示位置 CMyWnd ((InitGame (: I
附录 3:可供两个人对弈的中国象棋程序 - 355 - pDC->SelectObject(pOldPen); pDC->SelectObject(pOldBrush); // 准备显示棋子名称的字体 CFont *pOldFont, fontStone; fontStone.CreateFont(40, 0, 0, 0, 400, FALSE, FALSE, 0, OEM_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH, "楷体"); pOldFont = pDC->SelectObject(&fontStone); int tx = m_rectStone.left+6; int ty = m_rectStone.top+6; pDC->SetBkMode(TRANSPARENT); // 棋子背景均为黄色,字分红、黑两色 pDC->SetTextColor(RGB(m_bRed?255:0, 0, 0)); pDC->TextOut(tx, ty, m_sName); pDC->SelectObject(pOldFont); } } // 将棋子放到指定位置 void CStone::MoveTo(int col, int row, CPlate &plate) { m_bSelected = FALSE; m_nCol = col; m_nRow = row; CPoint pos = plate.GetPosition(col, row); m_rectStone = CRect(pos.x-m_nR, pos.y-m_nR, pos.x+m_nR, pos.y+m_nR); } // 框架窗口类 class CMyWnd: public CFrameWnd { CPlate m_Plate; // 棋盘 CStone m_StoneList[32]; // 棋子数组 BOOL m_bRedTurn; // 轮红方下 BOOL m_bSelectOne; // 已选择一棋子 int m_nWhichStone; // 被选择棋子的编号 CRect m_rectInfo; // 信息显示位置 public: CMyWnd(){InitGame();}
附录3:可供两个人对弈的中国象棋程序 356 void InitGame o BOOL KillSelfStone (int col, int row, BOOL red) int KillEnemy(int col, int row, BOOL red) void MoveStone( CPoint point) void Select Stone(CPoint point) void Go(CPoint) BOOL Move To (int, int) nt o afx msg void OnLBut ton Down UINT n Flags, CPoint point) DECLARE MESSAGE MAP O //消息映射 BEGIN MESSAGE MAP(CMyWnd, CFrameWnd) ON WM PAINT O ON WM LBUTTONDOWN O END MESSAGE MAP O //框架窗口类的成员函数 /初始化棋局 void CMyWnd: InitGame o m bRedTurn TRUE m sElectoN m reciNto CRect(315,480,515,550) oneList[ 0]= CStone ( true, 0, 0,"4", 3, m Plate) m StoneList[ 1]= CStone (True, 1, 0,y",4, m Plate m StoneList[ 2]= CStone(True, 2,0,"t", 5, m Plate) m StoneList[ 3]=CStone(True, 3, 0,"t, 6, m Plate m StoneList[ 4]= CStone(True, 4,, 7, m Plate) m StoneList[ 5]= CStone(TrUe, 5, 0, "t", 6, m Plate) m StoneList[ 6]= CStone (True, 6,0,"a", 5, m Plate) m StoneList[ 7]= CStone(True, 7, 0, 4, m Plate) m StoneList[ 8]= CStone(true, 8,, 3, m Plate) m StoneList[ 9]= CStone (True, 1, 2,0,2, m Plate) m StoneList[10] CStone(True, 7, 2,0,2, m Plate) m StoneList [11] CStone (true, 0, 3, R", 1, m Plate m StoneList [12]= CStone(true, 2, 3, R", 1, m Plate)
附录 3:可供两个人对弈的中国象棋程序 - 356 - void InitGame(); void ShowInfo(CDC *pDC); BOOL KillSelfStone(int col, int row, BOOL red); int KillEnemy(int col, int row, BOOL red); void MoveStone(CPoint point); void SelectStone(CPoint point); void Go(CPoint); BOOL MoveTo(int, int); protected: afx_msg void OnPaint(); afx_msg void OnLButtonDown(UINT nFlags, CPoint point); DECLARE_MESSAGE_MAP() }; // 消息映射 BEGIN_MESSAGE_MAP(CMyWnd,CFrameWnd) ON_WM_PAINT() ON_WM_LBUTTONDOWN() END_MESSAGE_MAP() // 框架窗口类的成员函数 // 初始化棋局 void CMyWnd::InitGame() { m_bRedTurn = TRUE; m_bSelectOne = FALSE; m_rectInfo = CRect(315, 480, 515, 550); m_StoneList[ 0] = CStone(TRUE, 0, 0, "车", 3, m_Plate); m_StoneList[ 1] = CStone(TRUE, 1, 0, "马", 4, m_Plate); m_StoneList[ 2] = CStone(TRUE, 2, 0, "象", 5, m_Plate); m_StoneList[ 3] = CStone(TRUE, 3, 0, "士", 6, m_Plate); m_StoneList[ 4] = CStone(TRUE, 4, 0, "将", 7, m_Plate); m_StoneList[ 5] = CStone(TRUE, 5, 0, "士", 6, m_Plate); m_StoneList[ 6] = CStone(TRUE, 6, 0, "象", 5, m_Plate); m_StoneList[ 7] = CStone(TRUE, 7, 0, "马", 4, m_Plate); m_StoneList[ 8] = CStone(TRUE, 8, 0, "车", 3, m_Plate); m_StoneList[ 9] = CStone(TRUE, 1, 2, "炮", 2, m_Plate); m_StoneList[10] = CStone(TRUE, 7, 2, "炮", 2, m_Plate); m_StoneList[11] = CStone(TRUE, 0, 3, "兵", 1, m_Plate); m_StoneList[12] = CStone(TRUE, 2, 3, "兵", 1, m_Plate);
附录3:可供两个人对弈的中国象棋程序 357 m StoneList[13]= CStone (True, 4, 3, R", 1, m Plate) m StoneList[14]= CStone (True, 6, 3, R", 1, m Plate) m StoneList [15]= CStone(True, 8, 3, R", 1, m Plate) m StoneList [16]= CStone (FALSe, 0, 9,"4,3, m Plate) m StoneList [17]= CStone(FALSe, 1, 9, n", 4, m Plate) m StoneList [18]= CStone(FALSe, 2,9,Na", 5, m Plate) m StoneList[19]= CStone(FALSe, 3, 9,"4t", 6, m Plate m StoneList [20]= CStone(FAlse, 4,9,"yf", 7, m Plate) m StoneList [21]= CStone(FALSe, 5, 9,"11,6, m Plate): m StoneList[22]= CStone(FALSe, 6, 9,ta", 5, m Plate m StoneList[23]= CStone(False, 7, 9,"y", 4, m Plate) m StoneList[25]= CStone(FALSe, 1, 7,"hi",2, m Plate m StoneList [26]= CStone(FALSE, 7, 7, *E, 2, m Plate m StoneList[27]= CStone(FALSe, 0, 6,"x", 1, m Plate) m StoneList[28]= CStone(FALSe, 2, 6,"x, 1, m Plate) m StoneList[29]= CStone(FALSe, 4, 6,3, 1, m Plate) m StoneList[30]= CStone(FALSe, 6, 6," x", 1, m Plate m StoneList [31]= CStone(FALSe, 8, 6,"x", 1, m Plate): /处理 WM ONPAINT消息,绘制窗口客户区(绘制棋盘,棋子等) void CMyWnd:: OnPaintO CPaintDC dc(this m Plate. ShowPlate(&dc) /显示棋盘 for (int i=0; i<32: i++) /显示所有棋子 StoneList [i]. ShowStone( &dc) ShowInfo(&dc) /显示轮谁行棋 /处理WM_ ONLBUTTONDOWN消息,移动棋子 void CMyWnd:: OnLBut ton Down (UINT nFlags, CPoint point) if( m eLectone)∥/已选择了要移动的棋子 MoveStone(point) else ∥/尚未选择要移动的棋子 SelectStone(point /移动棋子
附录 3:可供两个人对弈的中国象棋程序 - 357 - m_StoneList[13] = CStone(TRUE, 4, 3, "兵", 1, m_Plate); m_StoneList[14] = CStone(TRUE, 6, 3, "兵", 1, m_Plate); m_StoneList[15] = CStone(TRUE, 8, 3, "兵", 1, m_Plate); m_StoneList[16] = CStone(FALSE, 0, 9, "车", 3, m_Plate); m_StoneList[17] = CStone(FALSE, 1, 9, "马", 4, m_Plate); m_StoneList[18] = CStone(FALSE, 2, 9, "相", 5, m_Plate); m_StoneList[19] = CStone(FALSE, 3, 9, "仕", 6, m_Plate); m_StoneList[20] = CStone(FALSE, 4, 9, "帅", 7, m_Plate); m_StoneList[21] = CStone(FALSE, 5, 9, "仕", 6, m_Plate); m_StoneList[22] = CStone(FALSE, 6, 9, "相", 5, m_Plate); m_StoneList[23] = CStone(FALSE, 7, 9, "马", 4, m_Plate); m_StoneList[24] = CStone(FALSE, 8, 9, "车", 3, m_Plate); m_StoneList[25] = CStone(FALSE, 1, 7, "炮", 2, m_Plate); m_StoneList[26] = CStone(FALSE, 7, 7, "炮", 2, m_Plate); m_StoneList[27] = CStone(FALSE, 0, 6, "卒", 1, m_Plate); m_StoneList[28] = CStone(FALSE, 2, 6, "卒", 1, m_Plate); m_StoneList[29] = CStone(FALSE, 4, 6, "卒", 1, m_Plate); m_StoneList[30] = CStone(FALSE, 6, 6, "卒", 1, m_Plate); m_StoneList[31] = CStone(FALSE, 8, 6, "卒", 1, m_Plate); } // 处理 WM_ONPAINT 消息, 绘制窗口客户区 (绘制棋盘, 棋子等) void CMyWnd::OnPaint() { CPaintDC dc(this); m_Plate.ShowPlate(&dc); // 显示棋盘 for(int i=0; i<32; i++) // 显示所有棋子 m_StoneList[i].ShowStone(&dc); ShowInfo(&dc); // 显示轮谁行棋 } // 处理 WM_ONLBUTTONDOWN 消息, 移动棋子 void CMyWnd::OnLButtonDown(UINT nFlags, CPoint point) { if(m_bSelectOne) // 已选择了要移动的棋子 MoveStone(point); else // 尚未选择要移动的棋子 SelectStone(point); } // 移动棋子
附录3:可供两个人对弈的中国象棋程序 358 void CMyWnd: MoveStone( CPoint point) /如果选择原来的棋子,作废原来的选择 if(m StoneList [m nWhichStone]. MouseOnStone(point)) m StoneList [m nWhichStone] SelectStone o bSelectone False InvalidateRect(m StoneList [m nWhichStone] GetRectO, FALSE) else//在棋盘其他位置行棋 (point) /走棋或吃棋 void CMyWnd:: Go(CPoint point) for( int col=0;col<9;col++)/检查鼠标是否指向某个棋盘交叉点 for (int row=0: row<10: row++) CPoint p=m Plate GetPosition(col, row) if(r. PtInRect( point)//鼠标指向该交叉点 f(KillSelfStone(col, row, m bRedTurn)) MessageBox("您竟然想吃自己人?!") m bRedTurn Move To(col, row) ∥/移到指定位置或吃子 BOOL CMyWnd:: MoveTo(int col, int row) //更新窗口客户区原来的棋子位置 InvalidateRect(m StoneList [m nWhichStone] GetRect O) /棋子移向新位置 m StoneList [m nWhichStone] MoveTo(col, row, m Plate) //更新窗口客户区新的棋子位置 InvalidateRect(m StoneList [m nWhichStone] GetRectO)
附录 3:可供两个人对弈的中国象棋程序 - 358 - void CMyWnd::MoveStone(CPoint point) { // 如果选择原来的棋子, 作废原来的选择 if(m_StoneList[m_nWhichStone].MouseOnStone(point)) { m_StoneList[m_nWhichStone].SelectStone(); m_bSelectOne = FALSE; InvalidateRect(m_StoneList[m_nWhichStone].GetRect(), FALSE); } else // 在棋盘其他位置行棋 Go(point); } // 走棋或吃棋 void CMyWnd::Go(CPoint point) { for(int col=0; col<9; col++) // 检查鼠标是否指向某个棋盘交叉点 for(int row=0; row<10; row++) { CPoint p = m_Plate.GetPosition(col, row); CRect r(p.x-23, p.y-23, p.x+23, p.y+23); if(r.PtInRect(point)) // 鼠标指向该交叉点 { if(KillSelfStone(col, row, m_bRedTurn)) MessageBox("您竟然想吃自己人?!"); else m_bRedTurn = MoveTo(col, row); } } } // 移到指定位置或吃子 BOOL CMyWnd::MoveTo(int col, int row) { // 更新窗口客户区原来的棋子位置 InvalidateRect(m_StoneList[m_nWhichStone].GetRect()); // 棋子移向新位置 m_StoneList[m_nWhichStone].MoveTo(col, row, m_Plate); // 更新窗口客户区新的棋子位置 InvalidateRect(m_StoneList[m_nWhichStone].GetRect());
附录3:可供两个人对弈的中国象棋程序 359 ∥/还原选择棋子标志 m bSelectone False /检查是否吃了对方的棋子 It i KillEnemy(col, row, m bRedTurn) if(i>=0)//确实吃了对方棋子 m StoneList[i]. Killlto: if(m StoneList [i]. GetType o= jIANG) if(m bRedTurn) MessageBox( m bRedturn?"红方胜!":"黑方胜!"); Game o Invalidate return tRi //更新窗口客户区提示信息位置 InvalidateRect(m rectInfo) return i m bRedTurn /选择棋子 void CMy Wnd:: SelectStone(CPoint point int nwhich =m bRedTurn?0: 16 ∥/逐个查看己方棋子是否被选中 for (int i=nwhich: i<nwhich+16: i++) if(m StoneList [i]. Mouse tone(point)) m StoneList[i]. SelectStoneo //更新窗口客户区被选中棋子的位置(该棋子要变色 InvalidateRect(m StoneList[i]. GetRect(, FALSE) m nWhichstone m bSelectone= TRUE break /显示轮谁行棋 void CMy Wnd: ShowInfo(CDC *pDC)
附录 3:可供两个人对弈的中国象棋程序 - 359 - // 还原选择棋子标志 m_bSelectOne = FALSE; // 检查是否吃了对方的棋子 int i = KillEnemy(col, row, m_bRedTurn); if(i>=0)// 确实吃了对方棋子 { m_StoneList[i].KillIt(); if(m_StoneList[i].GetType() == JIANG) { if(m_bRedTurn) MessageBox(m_bRedTurn?"红方胜!":"黑方胜!"); InitGame(); Invalidate(); return TRUE; } } // 更新窗口客户区提示信息位置 InvalidateRect(m_rectInfo); return !m_bRedTurn; } // 选择棋子 void CMyWnd::SelectStone(CPoint point) { int nwhich = m_bRedTurn?0:16; // 逐个查看己方棋子是否被选中 for(int i=nwhich; i<nwhich+16; i++) if(m_StoneList[i].MouseOnStone(point)) { m_StoneList[i].SelectStone(); // 更新窗口客户区被选中棋子的位置(该棋子要变色) InvalidateRect(m_StoneList[i].GetRect(), FALSE); m_nWhichStone = i; m_bSelectOne= TRUE; break; } } // 显示轮谁行棋 void CMyWnd::ShowInfo(CDC *pDC)