📄 bwchessdlg.cpp
字号:
if(m_byColor)
DrawBitmap(dc,xx1,yy1,IDB_CANPLACE2, SRCCOPY);
else
DrawBitmap(dc,xx1,yy1,IDB_CANPLACE1, SRCCOPY);
}while(length);
if(m_byColor)
wsp.CopyBackIndex();
else
bsp.CopyBackIndex();
m_PeekOnce=1;
ReleaseDC(dc);
}
void CBWChessDlg::OnSetting() //响应“设置”命令
{
CSettingDlg dlg;
dlg.DoModal ();//显示“设置”对话框
if(g_bTopMost)
SetWindowPos(&wndTopMost,0,0,0,0,SWP_NOMOVE | SWP_NOSIZE);
else
SetWindowPos(&wndNoTopMost,0,0,0,0,SWP_NOMOVE | SWP_NOSIZE);
}
void CBWChessDlg::OnOpen() //响应“OPEN”命令
{
if(!m_bGameOver && g_bPrompt)
if(MsgBox(IDS_ABORT,IDS_TITLE_CHINESE,2)==IDCANCEL)
return ;
TCHAR sFilter[50]="BWChess File (*.BWS)|*.BWS||";
CFileDialog dlg(TRUE,NULL,NULL,OFN_HIDEREADONLY | OFN_OVERWRITEPROMPT,
sFilter);
int result=dlg.DoModal();
if(result==IDOK)
{
CFile file(dlg.GetPathName(), CFile::modeRead);
int buffer[9000],len,t;
unsigned int reallen=file.Read(buffer,9000*sizeof(int));
if((reallen!=(buffer[0]*sizeof(int))) || (reallen<140))
{
MsgBox(IDS_OPENERROR1,IDS_TITLE_CHINESE);
return;
}
if(buffer[1]!=EDITION)
{
MsgBox(IDS_OPENERROR2,IDS_TITLE_CHINESE);
return;
}
if(buffer[2])
{
MsgBox(IDS_OPENERROR3,IDS_TITLE_CHINESE);
return;
}
int i,j;
len=buffer[0]/2-1;
BOOL changeI=FALSE;
for(t=0;t<len;t++)
{
if(buffer[t+3]!=buffer[3+len+t])
{
changeI=TRUE;
break;
}
}
if(changeI)
{
MsgBox(IDS_OPENERROR1,IDS_TITLE_CHINESE);
return;
}
if(m_TimerOn)
{
KillTimer(PASSEDTIME);
m_TimerOn=0;
}
m_bGameOver = FALSE;
m_Skip=0;
i=0;
g_nStoneNum=0;
m_HintOnce=0;//0 for have not hinted yet,1 for have hinted
m_PeekOnce=g_bPeepOften;
m_IsGameStart=0;
ListInfo.destroy();
m_ListInfo.ResetContent();
if(!m_UndoPoint.IsEmpty())
m_UndoPoint.Destroy();
len=3;///important
m_byColor=buffer[len++];
g_nRunMode=buffer[len++];
m_PassedTime=buffer[len++];
m_PassedTime0=buffer[len++];
g_nSkill=buffer[len++];
g_bUserBlack=buffer[len++];
m_HintTime0=buffer[len++];
m_HintTime1=buffer[len++];
g_nTimeLimit=buffer[len++];
g_nIsNoTimeLimit=buffer[len++];
len+=5;
for(i=0;i<NUM;i++)
for(j=0;j<NUM;j++)
kernel[i][j]=buffer[len++];
int x,y,num,tc;
num=buffer[len++];
while(num>0)
{
x=buffer[len++];
y=buffer[len++];
tc=buffer[len++];
AddStringToList(x,y,tc);
num--;
}
//read m_UndoPoint
num=buffer[len++];
while(num>0)
{
int temp[NUM*NUM];
for(x=0;x<NUM*NUM;x++)
temp[x]=buffer[len++];
tc=buffer[len++];
m_UndoPoint.push(temp,tc);
num--;
}
IsEnd(1);
Calcu_BW();
SetChessTitle();
m_pMenu->EnableMenuItem(IDM_SAVEINFO,MF_GRAYED);
m_pMenu->EnableMenuItem(IDM_SAVE,MF_ENABLED);
m_pMenu->EnableMenuItem(IDM_HINT,MF_ENABLED);
m_pMenu->EnableMenuItem(IDM_UNDO,MF_ENABLED);
m_pMenu->EnableMenuItem(IDM_CANPLACE,MF_ENABLED);
m_pMenu->EnableMenuItem(IDM_REPLAY,MF_GRAYED);
InvalidateRect(NULL,TRUE);
SetTimer(PASSEDTIME,1000,NULL);
m_TimerOn=1;
}
}
void CBWChessDlg::OnSave() //响应“SAVE”命令
{
TCHAR sFilter[50]=_T("BWChess File (*.BWS)|*.BWS||");
TCHAR sExt[10]=_T("BWS");
CFileDialog dlg(FALSE,sExt,NULL,OFN_HIDEREADONLY | OFN_OVERWRITEPROMPT,
sFilter);
if(dlg.DoModal()==IDOK)
{
CFile file(dlg.GetPathName(),CFile::modeCreate | CFile::modeWrite);
int buffer[9000],len=3;// the buffer need about 4000 size
for(int ii=0;ii<2;ii++)//copy twice
{
buffer[len++]=m_byColor;
buffer[len++]=g_nRunMode;
buffer[len++]=m_PassedTime;
buffer[len++]=m_PassedTime0;
buffer[len++]=g_nSkill;
buffer[len++]=g_bUserBlack;
buffer[len++]=m_HintTime0;
buffer[len++]=m_HintTime1;
buffer[len++]=g_nTimeLimit;
buffer[len++]=g_nIsNoTimeLimit;
//restore 5 position for future use
buffer[len++]=0;
buffer[len++]=0;
buffer[len++]=0;
buffer[len++]=0;
buffer[len++]=0;
int i,j;
for(i=0;i<NUM;i++)
for(j=0;j<NUM;j++)
buffer[len++]=kernel[i][j];
int num=ListInfo.Len();
buffer[len++]=num;
int x,y,tc;
int re;
stack ts;
do
{
re=ListInfo.GetNextPos(&x,&y,&tc);
ts.push(x,y);
ts.SetMarks (tc);
}
while(re);
do
{
re=ts.GetNextPos(&x,&y,&tc);
buffer[len++]=x;
buffer[len++]=y;
buffer[len++]=tc;
}
while(re);
ListInfo.CopyBackIndex();
// store m_UndoPoint
int tlen=m_UndoPoint.Len();
buffer[len++]=tlen;
int tempUndo[NUM*NUM];
do
{
re=m_UndoPoint.GetNextPos(tempUndo,&tc);
for(x=0;x<NUM*NUM;x++)
buffer[len++]=tempUndo[x];
buffer[len++]=tc;
}
while(re);
m_UndoPoint.CopyBackIndex();
}
buffer[0]=len;
buffer[1]=EDITION;//this the edition of the banben
buffer[2]=(int)m_bGameOver;
file.Write(buffer,len*sizeof(int));
}
}
void CBWChessDlg::AddStringToList(int x, int y, int color,int win)//加入信息于列表框
{
CString str;
int result=m_ListInfo.GetCount();
if(!win)
{
if(color)
str.LoadString(IDS_SBLACK);// “%2d.黑棋: %c %d”
else
str.LoadString(IDS_SWHITE);
TCHAR s[100];
wsprintf(s, str.GetBuffer(256),result+1, y+65,x+1);
m_ListInfo.AddString(s);
ListInfo.push(x,y);
ListInfo.SetMarks(color);
}
else
{
if(win==1)//白 win
str.LoadString(IDS_WHITEWIN_CHINESE);
else if(win==2)//黑 win
str.LoadString(IDS_BLACKWIN_CHINESE);
else//本局平局
str.LoadString(IDS_TIE);
m_ListInfo.AddString(str);
}
m_ListInfo.SetCurSel(result);//将当前新加入的显色(兰色)
m_ListInfo.SetFocus();
}
void CBWChessDlg::RemoveStringFromList()//于列表框删除信息
{
int index=m_ListInfo.GetCount();
m_ListInfo.DeleteString(index-1);
int x,y;
ListInfo.pop(&x,&y);
ListInfo.GetTop(x,y);
m_CurPt.x =x,m_CurPt.y=y;
index=m_ListInfo.GetCount();
if(index)
{
m_ListInfo.SetCurSel(index-1);
m_ListInfo.SetFocus();
}
}
void CBWChessDlg::OnSaveinfo() //响应“导出走棋信息”
{
TCHAR sFilter[50]=_T("文本文件(*.TXT)|*.TXT||");
TCHAR sExt[10]=_T("txt");
CFileDialog dlg(FALSE,sExt,NULL,OFN_HIDEREADONLY | OFN_OVERWRITEPROMPT,
sFilter);
if(dlg.DoModal()==IDOK)
{
CFile file(dlg.GetPathName(),CFile::modeCreate | CFile::modeWrite | CFile::typeText);
TCHAR buffer[300];
int len=0,index=0;
len=GetWindowText(buffer,300);
buffer[len++]=13;
buffer[len++]=10;
file.Write(buffer,len);
len=m_ListInfo.GetCount();
while(index<len)
{
int slen=m_ListInfo.GetText(index++,buffer);
buffer[slen]=13;
buffer[slen+1]=10;
file.Write(buffer,slen+2);
}
}
}
BOOL CBWChessDlg::PreTranslateMessage(MSG* pMsg) //检测加速键消息是否被处理了
{//The TranslateAccelerator function processes accelerator keys for menu commands
if(!::TranslateAccelerator(m_hWnd,hAccelerator, pMsg))
return CDialog::PreTranslateMessage(pMsg);
return TRUE;
}
void CBWChessDlg::SetChessTitle()//载入标题
{
CString str;
if (g_nRunMode==MODE_WITH_COMPUTER && g_bUserBlack)
str.LoadString(IDS_SINGLE_USER_CHINESE);//“黑白棋: 与计算机对弈, 你执黑先下”
else if (g_nRunMode==MODE_WITH_COMPUTER && !g_bUserBlack)
str.LoadString(IDS_SINGLE_COMPUTER_CHINESE);//“黑白棋: 与计算机对弈, 计算机执黑先下”
else if (g_nRunMode==MODE_2PLAYER)
{
if(g_nIsNoTimeLimit)
str.LoadString(IDS_DOUBLE_NOLIMIT_CHINESE);//“黑白棋: 双人同机对弈,不限时”
else
{
str.LoadString(IDS_DOUBLE_LIMIT_CHINESE);//“黑白棋: 双人同机对弈,限时%d秒”
TCHAR str1[200];
wsprintf(str1, str.GetBuffer(256), g_nTimeLimit);
str=str1;
}
}
SetWindowText(str);//显示标题
}
void CBWChessDlg::OnListDoubleClicked()//双击列表,撤消操作
{
if(m_bGameOver || g_nIsDemo)//游戏已结束或正在演示
return;
int nSel=m_ListInfo.GetCurSel();
int length=m_ListInfo.GetCount()-1;
while(length>=nSel)//依次进行撤消
{
OnUndo();
length=m_ListInfo.GetCount()-1;
}
}
void CBWChessDlg::DrawFrame(CDC *dc)//画棋盘
{
const int Sx=1;
const int Sy=1;
int i,j;
int wx0,wy0,wx1,wy1;
wx0=Sx,wy0=Sy;
DrawBitmap(dc,wx0,wy0,IDB_F1_1,SRCCOPY);
wx0=Sx+m_wFrameHeight+NUM*m_wFrameWidth,wy0=Sy;
DrawBitmap(dc,wx0,wy0,IDB_F1_10,SRCCOPY);
wx0=Sx,wy0=Sy+m_wFrameHeight+NUM*m_wStoneHeight;
DrawBitmap(dc,wx0,wy0,IDB_F10_1,SRCCOPY);
wx0=Sx+m_wFrameHeight+NUM*m_wStoneWidth,wy0=Sy+m_wFrameHeight+NUM*m_wStoneHeight;
DrawBitmap(dc,wx0,wy0,IDB_F10_10,SRCCOPY);
wx0=Sx+m_wFrameHeight,wy0=Sy,wx1=Sx+m_wFrameHeight,wy1=Sy+m_wFrameHeight+m_wStoneWidth*NUM;
for(i=1,wx0=Sx+m_wFrameHeight,wy0=Sy,wx1=Sx+m_wFrameHeight,wy1=Sy+m_wFrameHeight+m_wStoneWidth*NUM;i<NUM+1;i++)
{//画水平的边框8格
DrawBitmap(dc,wx0,wy0,IDB_F1_2+i-1,SRCCOPY);
DrawBitmap(dc,wx1,wy1,IDB_F10_2+i-1,SRCCOPY);
wx0+=m_wFrameWidth;
wx1+=m_wFrameWidth;
}
for(i=0,wx0=Sx,wy0=Sy+m_wFrameHeight,wx1=Sx+m_wFrameHeight+NUM*m_wStoneWidth,wy1=Sy+m_wFrameHeight;i<NUM;i++)
{//画垂直的边框8格
DrawBitmap(dc,wx0,wy0,IDB_F2_1+i,SRCCOPY);
DrawBitmap(dc,wx1,wy1,IDB_F2_10+i,SRCCOPY);
wy0+=m_wStoneHeight;
wy1+=m_wStoneHeight;
}
for(i=0,wx0=Sx+m_wFrameHeight,wy0=Sy+m_wFrameHeight;i<NUM;i++,wx0=Sx+m_wFrameHeight,wy0=i*m_wStoneHeight+Sy+m_wFrameHeight)
for(j=0;j<NUM;j++,wx0+=m_wStoneWidth)
{//画棋盘8*8
if(!kernel[i][j])
{
CPoint pt(wx0,wy0);
DrawBitmap(dc,wx0,wy0,IDB_EMPTY,SRCCOPY);
}
}
}
void CBWChessDlg::OnDemo() //响应“计算机演示/终止计算机对弈”命令
{
CString str;
if(g_nIsDemo)//响应“终止计算机对弈”命令
{
::TerminateThread(m_CcThread->m_hThread,0);
m_pMenu->EnableMenuItem(IDM_NEW,MF_ENABLED);
m_pMenu->EnableMenuItem(IDM_OPEN,MF_ENABLED);
m_pMenu->EnableMenuItem(IDM_SAVE,MF_ENABLED);
m_pMenu->EnableMenuItem(IDM_NETPLAY,MF_ENABLED);
m_pMenu->EnableMenuItem(IDM_REPLAY,MF_ENABLED);
str.LoadString(IDS_DEMOTITLE0);//“计算机演示[&M]...\tCtrl+M”
m_pMenu->ModifyMenu(IDM_DEMO,MF_BYCOMMAND | MF_STRING,IDM_DEMO,str);
//程序已经在“演示”,菜单已被改为“终止计算机对弈”,因此现在要恢复为“计算机演示”
g_nIsDemo=0;
m_bGameOver=TRUE;
}
else//响应“计算机演示”命令
{
int HaveKilled=0;
if(m_TimerOn)//终止计时
{
HaveKilled=1;
KillTimer(PASSEDTIME);
m_TimerOn=0;
}
if(!m_bGameOver && g_bPrompt)//游戏没有结束
{
if(MsgBox(IDS_ABORT,IDS_TITLE_CHINESE,2)==IDCANCEL)
{//弹出对话框询问
if(HaveKilled)//取消对话框,恢复计时
{
SetTimer(PASSEDTIME,1000,NULL);
m_TimerOn=1;
}
return;
}
}
//OK对话框
CDemo dlg;//弹出计算机对弈对话框
if(dlg.DoModal()==IDCANCEL)
{
if(HaveKilled)
{
SetTimer(PASSEDTIME,1000,NULL);
m_TimerOn=1;
}
return;
}
//修改菜单
m_pMenu->EnableMenuItem(IDM_HINT,MF_GRAYED);
m_pMenu->EnableMenuItem(IDM_UNDO,MF_GRAYED);
m_pMenu->EnableMenuItem(IDM_CANPLACE,MF_GRAYED);
m_pMenu->EnableMenuItem(IDM_SAVE,MF_GRAYED);
m_pMenu->EnableMenuItem(IDM_SAVEINFO,MF_GRAYED);
m_pMenu->EnableMenuItem(IDM_NEW,MF_GRAYED);
m_pMenu->EnableMenuItem(IDM_OPEN,MF_GRAYED);
m_pMenu->EnableMenuItem(IDM_NETPLAY,MF_GRAYED);
m_pMenu->EnableMenuItem(IDM_REPLAY,MF_GRAYED);
str.LoadString(IDS_DEMOTITLE1);
m_pMenu->ModifyMenu(IDM_DEMO,MF_BYCOMMAND | MF_STRING,IDM_DEMO,str);
//修改菜单为“终止计算机对弈”
int flag=0;//标志是否为历史棋局
if(dlg.m_IsFile)//演示历史棋局
{
CFile file(dlg.m_FilePath, CFile::modeRead);
int buffer[9000],len;
file.Read(buffer,9000*sizeof(int));
len=18+NUM*NUM;///important
m_PointGo.destroy();
int x,y,num,tc;
stack tt;
num=buffer[len++];//num代表走棋的步数
while(num>0)//进栈
{
x=buffer[len++];
y=buffer[len++];
tc=buffer[len++];
tt.push(x,y);
tt.SetMarks(tc);
num--;
}
while(!tt.isempty ())//再出栈入栈,顺序演示
{
tc=tt.GetMarks (0);
tt.pop (&x,&y);
m_PointGo.push(x,y);
m_PointGo.SetMarks(tc);
}
flag=0;
}
else//不是历史棋局
{
CString str1;
switch(g_nCbSkill)//黑方级别
{
case 1://黑方:初级
switch(g_nCwSkill)//白方级别
{
case 1://白方:初级
str1.LoadString(IDS_DEMO_TITLE_11);
//“黑白棋:计算机演示->黑方:初级;白方:初级”
break;
case 2://白方:中级
str1.LoadString(IDS_DEMO_TITLE_12);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -