?? mainform1.cpp
字號:
/*
主菜單項“忽略”事件處理函數
把主窗體中棋盤上編輯過的棋子全部作廢。
*/
void __fastcall TMainForm::CancelClick(TObject *Sender)
{
memcpy(ChessBoard, SaveChessBoard, sizeof(BOARDTYPE) * 0x99);
ResetNewPos();
NormalSetup();
}
//---------------------------------------------------------------------------
/*
自定義正常設置函數
InfoForm->BringToFront()將信息子窗體InfoForm推到前端。
恢復棋子在主窗體上的原始位置。
*/
void TMainForm::NormalSetup()
{
InfoForm->BringToFront();
MainForm->Menu=TChessMenu; //動態設置主窗體主菜單
delete[] SaveChessBoard;
Editing = EditingChessBoard = false;
UpdateChessBoard();
}
//---------------------------------------------------------------------------
/*
主菜單項“演示模式”事件處理函數
程序輪流成為紅方、黑方,即自己與自己對弈。
*/
void __fastcall TMainForm::DemoClick(TObject *Sender)
{
extern bool AutoPlay;
bool IsEasy = false;
if (Level == easygame)
{
IsEasy = true;
Level = normal;
HideAttacks();
}
AutoPlay = true;
ComputersTurn();
if (IsEasy)
{
Level = easygame;
UpdateChessBoard();
}
CurPlayer = Player;
ComputerColor = Opponent;
PrintCurLevel();
}
//---------------------------------------------------------------------------
/*
主菜單項“無限制”事件處理函數
改變信息窗體中信息提示為無限制
程序無限制地加大深度搜索最好的一步棋。
*/
void __fastcall TMainForm::InfiniteClick(TObject *Sender)
{
if (Level != infinite)
{
UnCheckLevelMenu(Level);
CheckMenuItem(TChessMenu->Handle, Infinite->Command, MF_CHECKED);
}
Level = infinite;
MaxLevel = MAXPLY;
PrintCurLevel();
}
//---------------------------------------------------------------------------
/*
主菜單項“將死搜索”事件處理函數
改變信息窗體中信息提示為將死搜索
程序無限制地加大深度直到搜索到能將死的一步棋。
當棋子比較多時,很難搜索到終局(將死)。
*/
void __fastcall TMainForm::MateClick(TObject *Sender)
{
if (Level != matesearch)
{
UnCheckLevelMenu(Level);
CheckMenuItem(TChessMenu->Handle, Mate->Command, MF_CHECKED);
}
Level = matesearch;
PrintCurLevel();
ComputersTurn();
}
//---------------------------------------------------------------------------
/*
主菜單項“回合搜索”事件處理函數
彈出“設置回合數”對話框。
在主菜單項“回合搜索”前打勾。
改變信息窗體中信息提示為所設置的回合數。
*/
void __fastcall TMainForm::Ply1Click(TObject *Sender)
{
char *PlySearchDepth = new char[40];
sprintf(PlySearchDepth, "%d", MaxLevel);
if (InputPlyDlg->ShowModal()== mrOk)
{
int NewPlyDepth = StrToInt(InputPlyDlg->Edit1->Text);
if (NewPlyDepth > 0)
{
if (Level != plysearch)
{
UnCheckLevelMenu(Level);
CheckMenuItem(TChessMenu->Handle, Ply1->Command, MF_CHECKED);
}
MaxLevel = (BYTE)((NewPlyDepth > MAXPLY) ? MAXPLY : NewPlyDepth);
Level = plysearch;
PrintCurLevel();
}
else
Error("數據不正確。請重輸。");
}
delete PlySearchDepth;
}
//---------------------------------------------------------------------------
/*
主菜單項“兩人對弈”事件處理函數
翻轉主菜單項“兩人對弈”為”單獨對弈“
*/
void __fastcall TMainForm::TwoPlayerClick(TObject *Sender)
{
static LEVELTYPE OldLevel = normal;
MultiMove = !MultiMove;
if (MultiMove)
{
TwoPlayer->Caption= "單獨對弈"; //動態改變菜單項文本
OldLevel = Level;
EnableMenuItem(TChessMenu->Handle, 2, MF_GRAYED | MF_BYPOSITION);
DrawMenuBar(MainForm->Handle);
Level = normal;
PrintCurLevel();
}
else
{
TwoPlayer->Caption = "兩人對弈"; //動態改變菜單項文本
EnableMenuItem(TChessMenu->Handle, 2, MF_ENABLED | MF_BYPOSITION);
/*
第一個參數為菜單句柄,從菜單TChessMenu句柄屬性Handle獲取。
第二個參數指明菜單的位置,即第三項。
第三個參數是一個標志集合。它告訴菜單項是應該執行哪一些操作
和如何被指明的。在這種情況下,MF_ENABLED告訴EnableMenuItem菜單項激活
MF_BYPOSITION告訴EnableMenuItem菜單項是用位置指明的。
*/
DrawMenuBar(MainForm->Handle);
Level = OldLevel;
PrintCurLevel();
}
}
//---------------------------------------------------------------------------
/*
主菜單項“反轉棋盤”事件處理函數
對換紅方和黑方的棋盤。
*/
void __fastcall TMainForm::ReverseClick(TObject *Sender)
{
Turned = !Turned;
PrintChessBoard();
}
//---------------------------------------------------------------------------
/*
主菜單項“悔棋”事件處理函數
至少要動過一次棋子,該菜單項才由灰色變為黑色(激活狀態)。
*/
void __fastcall TMainForm::UndoMoveClick(TObject *Sender)
{
if (ComputerThinking)
{
MessageToPost = IDM_UNDO;
return;
}
if (!Undo())
UndoMove->Enabled = false;
RedoUndo->Enabled = true;
CurPlayer = Player;
ComputerColor = Opponent;
}
//---------------------------------------------------------------------------
/*
主菜單項“重下”事件處理函數
至少要悔過一次棋子,該菜單項才由灰色變為黑色(激活狀態)。
*/
void __fastcall TMainForm::RedoUndoClick(TObject *Sender)
{
if (ComputerThinking)
{
MessageToPost = IDM_REDO;
return;
}
if (!Redo())
RedoUndo->Enabled = false;
UndoMove->Enabled = true;
CurPlayer = Player;
ComputerColor = Opponent;
}
//---------------------------------------------------------------------------
/*
自定義子菜單項加勾函數
選中子菜單項”容易“、”每次移動時間“、”總時間“、”匹配“、
”無限制“、”回合搜索“、”將死搜索“ 之一時,在該項前打勾。
*/
void TMainForm::CheckLevelMenu(LEVELTYPE level)
{
int CheckItem = Easy->Command;
switch (level)
{
case normal :
CheckItem = MoveTime->Command;
break;
case fullgametime :
CheckItem = TotalTime->Command;
break;
case plysearch :
CheckItem = Ply1->Command;
break;
case easygame :
CheckItem = Easy->Command;
break;
case infinite :
CheckItem = Infinite->Command;
break;
case matesearch :
CheckItem = Mate->Command;
break;
case matching :
CheckItem = Matching->Command;
break;
}
CheckMenuItem(TChessMenu->Handle, CheckItem, MF_CHECKED);
}
/*
自定義子菜單項去勾函數
改變選中子菜單項”容易“、”每次移動時間“、”總時間“、”匹配“、
”無限制“、”回合搜索“、”將死搜索“ 之一時,在該項前去掉勾。
*/
void TMainForm::UnCheckLevelMenu(LEVELTYPE level)
{
int CheckItem = Easy->Command;
switch (level)
{
case normal :
CheckItem = MoveTime->Command;
break;
case fullgametime :
CheckItem = TotalTime->Command;
break;
case plysearch :
CheckItem = Ply1->Command;
break;
case easygame :
CheckItem = Easy->Command;
break;
case infinite :
CheckItem = Infinite->Command;
break;
case matesearch :
CheckItem = Mate->Command;
break;
case matching :
CheckItem = Matching->Command;
break;
}
CheckMenuItem(TChessMenu->Handle, CheckItem, MF_UNCHECKED);
}
//---------------------------------------------------------------------------
/*
主菜單項“容易”事件處理函數
選中子菜單項”容易“時,在該項前打勾。
對弈時在棋盤上對下一步要吃掉的棋子用正方形框住。
*/
void __fastcall TMainForm::EasyClick(TObject *Sender)
{
if (Level != easygame)
{
UnCheckLevelMenu(Level);
CheckMenuItem(TChessMenu->Handle, Easy->Command, MF_CHECKED);
}
Level = easygame;
AverageTime = 5.;
MaxLevel = MAXPLY;
PrintCurLevel();
}
//---------------------------------------------------------------------------
/*
主菜單項“完成”事件處理函數
測試棋盤中的棋子擺放是否正確。如果不正確,則彈出錯誤對話框,
直至正確才退出編輯狀態。
*/
void __fastcall TMainForm::DoneClick(TObject *Sender)
{
SQUARETYPE sq;
int TotalCount[2] = { 0, 0 };
int KingCount[2] = { 0, 0 };
int AssistCount[2] = { 0, 0};
int BishopCount[2] = { 0, 0 };
int KnightCount[2] = { 0, 0 };
int RookCount[2] = { 0, 0 };
int GunnerCount[2] = { 0, 0 };
int PawnCount[2] = { 0, 0 };
bool Done = false;
bool RKingNumDone, BKingNumDone, RAssistNumDone, BAssistNumDone;
bool RBishopNumDone, BBishopNumDone, RKnightNumDone, BKnightNumDone;
bool RRookNumDone, BRookNumDone, RGunnerNumDone, BGunnerNumDone;
bool RPawnNumDone, BPawnNumDone;
RKingNumDone = BKingNumDone = RAssistNumDone = BAssistNumDone = true;
RBishopNumDone = BBishopNumDone = RKnightNumDone = BKnightNumDone = true;
RRookNumDone = BRookNumDone = RGunnerNumDone = BGunnerNumDone = true;
RPawnNumDone = BPawnNumDone = true;
bool RKingPosDone, BKingPosDone, RAssistPosDone, BAssistPosDone;
bool RBishopPosDone, BBishopPosDone, RPawnPosDone, BPawnPosDone;
RKingPosDone = BKingPosDone = RAssistPosDone = BAssistPosDone = true;
RBishopPosDone = BBishopPosDone = RPawnPosDone = BPawnPosDone = true;
AnsiString ErrorNumText = "";
AnsiString ErrorPosText = "";
if (Modified)
{
for (sq = 0; sq < 0x99; sq++)
if (((sq>>4)<10) && ((sq % 16)<9) && ((sq | 0xff)>=0))
{
if (ChessBoard[sq].piece != empty)
{
TotalCount[ChessBoard[sq].color]++;
if (ChessBoard[sq].piece == king)
KingCount[ChessBoard[sq].color]++;
if (ChessBoard[sq].piece == assist)
AssistCount[ChessBoard[sq].color]++;
if (ChessBoard[sq].piece == bishop)
BishopCount[ChessBoard[sq].color]++;
if (ChessBoard[sq].piece == knight)
KnightCount[ChessBoard[sq].color]++;
if (ChessBoard[sq].piece == rook)
RookCount[ChessBoard[sq].color]++;
if (ChessBoard[sq].piece == gunner)
GunnerCount[ChessBoard[sq].color]++;
if (ChessBoard[sq].piece == pawn)
PawnCount[ChessBoard[sq].color]++;
}
}
if (KingCount[red] != 1)
{
ErrorNumText = "帥";
RKingNumDone = false;
}
if (KingCount[black] != 1)
{
ErrorNumText = ErrorNumText + "將";
BKingNumDone = false;
}
if (AssistCount[red] > 2)
{
ErrorNumText = ErrorNumText + "仕";
RAssistNumDone = false;
}
if (AssistCount[black] > 2)
{
ErrorNumText = ErrorNumText + "士";
BAssistNumDone = false;
}
if (BishopCount[red] > 2)
{
ErrorNumText = ErrorNumText + "相";
RBishopNumDone = false;
}
if (BishopCount[black] > 2)
{
ErrorNumText = ErrorNumText + "象";
BBishopNumDone = false;
}
if ((KnightCount[red] > 2 ) ||( KnightCount[black] > 2))
{
ErrorNumText = ErrorNumText + "馬";
RKnightNumDone = BKnightNumDone = false;
}
if ((RookCount[red] >2 )||( RookCount[black] >2 ))
{
ErrorNumText = ErrorNumText + "車";
RRookNumDone = BRookNumDone = false;
}
if ( GunnerCount[red] > 2)
{
ErrorNumText = ErrorNumText + "炮";
RGunnerNumDone = false;
}
if ( GunnerCount[black] > 2)
{
ErrorNumText = ErrorNumText + "砲";
BGunnerNumDone = false;
}
if (PawnCount[red] > 5)
{
ErrorNumText = ErrorNumText + "兵";
RPawnNumDone = false;
}
if (PawnCount[black] > 5)
{
ErrorNumText = ErrorNumText + "卒";
BPawnNumDone = false;
}
ErrorNumText = ErrorNumText + "的數目不正確";
for (sq = 0; sq < 0x99; sq++)
if (((sq>>4)<10) && ((sq % 16)<9) && ((sq | 0xff)>=0))
{
if (ChessBoard[sq].color == red)
if (ChessBoard[sq].piece == king)
if (((sq >> 4) > 2) || ((sq % 16) > 5) || ((sq % 16) < 3))
RKingPosDone = false;
if (ChessBoard[sq].color == black)
if (ChessBoard[sq].piece == king)
if (((sq >> 4) < 7) || ((sq % 16) > 5) || ((sq % 16) < 3))
BKingPosDone = false;
if (ChessBoard[sq].color == red)
if (ChessBoard[sq].piece == assist)
{
if (((sq >> 4) > 2) || ((sq % 16) > 5) || ((sq % 16) < 3))
RAssistPosDone = false;
if ((sq == 0x13) || (sq == 0x15)||(sq == 4)||(sq == 0x24))
RAssistPosDone = false;
}
if (ChessBoard[sq].color == black)
if (ChessBoard[sq].piece == assist)
{
if (((sq >> 4) < 7) || ((sq % 16) > 5) || ((sq % 16) < 3))
BAssistPosDone = false;
if ((sq == 0x83) || (sq == 0x55)||(sq == 0x94)||(sq == 0x74))
BAssistPosDone = false;
}
if (ChessBoard[sq].color == red)
if (ChessBoard[sq].piece == bishop)
if ((sq != 2) && (sq != 6) && (sq != 0x20) && (sq != 0x24)
&& (sq != 0x28) && (sq != 0x42) && (sq != 0x46))
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -