1156 lines
40 KiB
C++
1156 lines
40 KiB
C++
#include <iostream>
|
|
#include<fstream>
|
|
#include<string>
|
|
#include<conio.h>
|
|
#include<cmath>
|
|
#include<ctime>
|
|
#include<cstdlib>
|
|
using namespace std;
|
|
|
|
|
|
// test of branch
|
|
|
|
|
|
int hello;
|
|
|
|
struct khone{
|
|
char color;
|
|
bool possible; // ایا امکان گذاشتن مهره در اینجا هست
|
|
};
|
|
|
|
struct player{ // اینم زیرمجموعه هاش واضحه چیه
|
|
string name;
|
|
char color;
|
|
int score;
|
|
};
|
|
|
|
khone** gameboard;
|
|
int gamesize;
|
|
player Player1;
|
|
player Player2;
|
|
player Robat;
|
|
bool singlemood = false; // اگه تو حات سینگل بودیم ربات فعال شه
|
|
bool turn = true; // true : player 1 : B false :player2 : W
|
|
int cursor_i = 0;
|
|
int cursor_j = 0;
|
|
int numberOfPossible = 0 ; // این برای شمارش تعداد جاهایی که میتونیم مهره بزاریم
|
|
bool nonexit = true; // این برای وقتی که exit میزنیم
|
|
|
|
// کاربرد توابع رو توضیح مختصر میدیم
|
|
|
|
|
|
|
|
void menu(); // تابع منو
|
|
void make(int n); // ساختن زمین بازی تو heap
|
|
void map(int n); // قرار دادن مهره های اولیه در بازی
|
|
void singlePlayer(); // گرفتن اطلاعات 1 بازیکن و فعال کردن سینگل مود
|
|
void twoPlayer(); // گرفتن اسم 2 تا بازیکن
|
|
void move(); // با توجه به کاراکتری که گرفتی جابجا میکنه و مهره میزاره
|
|
void robatMove(); // حوش مثنوعی رباط
|
|
void letsPlay(); // مراحل انجام بازی در این تابع
|
|
void checkPossible(int i , int j); // برای هر خونه بررسی میکنه میتونیم مهره بزاریم یا نه
|
|
void clearPossible(); // تو هیچ خونه ای نمیتونیم مهره بزاریم یه جورایی حکم ریست کردن داره
|
|
void checkSurround(int i , int j); // محاصره شدن مهره وسط مهره حریف رو بررسی میکنه و برعکس میکنه
|
|
void printMap(); // نقشه رو با کرسر و مکان های پیشنهادی و مخلفات نشون میده
|
|
void justPrint(); // فقط رنگ های نقشه رو نشون میده
|
|
void countscore();
|
|
void result(); // اینم بعد تموم شدن بازی نتیجه رو نشون میده و تو فایل دیگه مینویسه
|
|
void countPossible(); // تعداد خونه هایی که میتونیم توش مهره بزاریم رو میمشماره
|
|
bool finish(); // چک میکنه ببینه پر شده یا نه صفحه
|
|
string getDateTime(); // ساعت گویا
|
|
void cleanIt(); // وظیفه پاک کردن هر چی داشتیم از heap
|
|
|
|
|
|
int main(){
|
|
srand(static_cast<unsigned int>(time(nullptr)));
|
|
system("chcp 65001"); // تغییر کدپیج به UTF-8
|
|
system("cls");
|
|
|
|
|
|
|
|
|
|
while (true){
|
|
|
|
menu();
|
|
if (!nonexit){
|
|
break ;
|
|
}
|
|
make(gamesize);
|
|
map(gamesize);
|
|
|
|
system("cls");
|
|
|
|
|
|
letsPlay();
|
|
turn = true;
|
|
|
|
|
|
|
|
cleanIt();
|
|
}
|
|
|
|
return 0 ;
|
|
}
|
|
|
|
void menu(){
|
|
system("cls");
|
|
cout << "1.Newgame" << endl;
|
|
cout << "2.Help" << endl;
|
|
cout << "3.Game History" << endl;
|
|
cout << "4.Exit" << endl;
|
|
int a;
|
|
cin >> a;
|
|
system("cls");
|
|
switch (a){
|
|
case 1 :
|
|
{
|
|
while (true){
|
|
cout << "Pleas Enter Size Of Game" << endl ;
|
|
cin >> gamesize;
|
|
system("cls");
|
|
if (gamesize % 2 == 0){
|
|
break;
|
|
}
|
|
cout << "Invalid ";
|
|
|
|
}
|
|
|
|
system("cls");
|
|
cout << "1.Single play"<<endl;
|
|
cout << "2.Two players"<<endl;
|
|
int a;
|
|
cin >> a;
|
|
if (a==1) singlePlayer();
|
|
else if (a==2) twoPlayer();
|
|
else menu();
|
|
break;
|
|
}
|
|
case 2:
|
|
{
|
|
ifstream helpfile("Help.txt");
|
|
string line;
|
|
|
|
if (helpfile.is_open()){
|
|
while(getline(helpfile , line)){
|
|
cout << line << endl;
|
|
}
|
|
helpfile.close();
|
|
}
|
|
else{
|
|
cout << "Help not opened" << endl ;
|
|
}
|
|
getch();
|
|
menu();
|
|
break;
|
|
}
|
|
case 3:
|
|
{
|
|
while (true){
|
|
cout << "1.Report Game History" << endl;
|
|
cout << "2.Delete Game History" << endl;
|
|
int a ;
|
|
cin >> a ;
|
|
system("cls");
|
|
if (a == 1){
|
|
ifstream gamefile("GameHistory.txt");
|
|
string line;
|
|
|
|
if (gamefile.is_open()){
|
|
while(getline(gamefile , line)){
|
|
cout << line << endl;
|
|
}
|
|
gamefile.close();
|
|
}
|
|
else{
|
|
cout << "Game history file not opened" << endl ;
|
|
}
|
|
getch();
|
|
menu();
|
|
break;
|
|
}
|
|
if(a==2){
|
|
ofstream file("GameHistory.txt", ios::trunc); // فایل باز میشه و محتوا پاک میشه
|
|
file.close();
|
|
cout << "Successfully deleted";
|
|
getch();
|
|
menu();
|
|
break ;
|
|
}
|
|
}
|
|
break;
|
|
}
|
|
case 4:
|
|
nonexit = false; // اگه این غلط شه انگار تابع main تمومه
|
|
break;
|
|
default:
|
|
menu();
|
|
break;
|
|
}
|
|
}
|
|
|
|
void make(int n){
|
|
gameboard = new khone*[gamesize];
|
|
for (int i = 0 ; i < gamesize ; i++){
|
|
gameboard[i] = new khone[gamesize];
|
|
|
|
}
|
|
}
|
|
|
|
void map(int n){
|
|
for (int i = 0 ; i < n ; i++){
|
|
for (int j = 0 ; j < n ; j++){
|
|
if (i == (n/2)-1 && j == (n/2)-1){
|
|
gameboard[i][j].color = 'W';
|
|
}
|
|
else if (i == (n/2) && j ==(n/2)){
|
|
gameboard[i][j].color = 'W';
|
|
}
|
|
else if (i == (n/2)-1 && j ==(n/2) ){
|
|
gameboard[i][j].color = 'B';
|
|
}
|
|
else if (i == (n/2) && j ==(n/2)-1){
|
|
gameboard[i][j].color = 'B';
|
|
}
|
|
else{
|
|
gameboard[i][j].color = '0';
|
|
}
|
|
gameboard[i][j].possible = false;
|
|
}
|
|
}
|
|
}
|
|
|
|
void singlePlayer(){
|
|
cout << "Please enter your name" << endl;
|
|
cin >> Player1.name;
|
|
Player2.name = "Robat" ;
|
|
Player1.color = 'B';
|
|
Player2.color = 'W';
|
|
singlemood = true ;
|
|
|
|
}
|
|
void twoPlayer(){
|
|
cout << "Please enter name of player1" << endl;
|
|
cin >> Player1.name;
|
|
cout << "Please enter name of player2" << endl;
|
|
cin >> Player2.name;
|
|
Player1.color = 'B';
|
|
Player2.color = 'W';
|
|
}
|
|
|
|
void move(){
|
|
char userInput;
|
|
do{
|
|
userInput = getch();
|
|
if (userInput == 'w' || userInput == 'W') cursor_i --;
|
|
if (userInput == 's' || userInput == 'S') cursor_i ++;
|
|
if (userInput == 'a' || userInput == 'A') cursor_j --;
|
|
if (userInput == 'd' || userInput == 'D') cursor_j ++;
|
|
if (userInput == '\r') { // اگه کاربر اینتر زد
|
|
while(cursor_i <0){ // اگه عدد منفی شد مثبت شه چون در نهایت به پیمانه میگیریم با اندازه جمع میکنیم
|
|
cursor_i = cursor_i + gamesize;
|
|
}
|
|
while(cursor_j <0){
|
|
cursor_j = cursor_j + gamesize;
|
|
}
|
|
if (cursor_i >= gamesize){ // اگرم از اندازه بازی بیشتر شد پیمانه میگیریم که بیفته تو محوطه
|
|
cursor_i = cursor_i % gamesize;
|
|
}
|
|
if(cursor_j >= gamesize){
|
|
cursor_j = cursor_j % gamesize ;
|
|
}
|
|
if(turn){ // رعایت نوبت
|
|
if(gameboard[cursor_i][cursor_j].color =='0' && gameboard[cursor_i][cursor_j].possible == true){
|
|
gameboard[cursor_i][cursor_j].color= 'B'; // خونه رو سیاه کن
|
|
checkSurround(cursor_i , cursor_j); // محاصره شدن رو هم بررسی کن
|
|
turn = !turn; // نوبت رو هم برگردون
|
|
}
|
|
else{
|
|
cout << "Invalid Move"; // اگه امکان گذاشتن مهره نبود نه نه نه بنویسه
|
|
getch();
|
|
}
|
|
}
|
|
else{
|
|
if(gameboard[cursor_i][cursor_j].color =='0' && gameboard[cursor_i][cursor_j].possible == true){
|
|
gameboard[cursor_i][cursor_j].color= 'W';
|
|
checkSurround(cursor_i , cursor_j);
|
|
turn = !turn;
|
|
}
|
|
else{
|
|
cout << "Invalid Move";
|
|
getch();
|
|
}
|
|
|
|
}
|
|
}
|
|
|
|
system("cls"); // پاکش کن
|
|
printMap(); // نقشه جدید رو نشون بده
|
|
|
|
|
|
}while(userInput != '\r');
|
|
}
|
|
|
|
void robatMove(){
|
|
clearPossible(); // همه چی از اول
|
|
for (int i = 0 ; i < gamesize ; i++){ // چیزایی که میتونه بزاره رو بررسی کن و تعدادش رو بگیر
|
|
for (int j = 0 ; j < gamesize ; j++){
|
|
checkPossible(i , j);
|
|
}
|
|
}
|
|
numberOfPossible = 0 ;
|
|
countPossible();
|
|
if (numberOfPossible == 0){ // اگه 0 بود که هیچی تو تابع لتس پلی pass میخورع
|
|
turn = !turn;
|
|
return;
|
|
}
|
|
int randomNum = rand() % numberOfPossible + 1 ; // اگه هم نه یه عدد انتخاب کن
|
|
for (int i = 0 ; i <gamesize ; i++){
|
|
for (int j = 0 ; j< gamesize ; j++){
|
|
if (gameboard[i][j].possible == true){
|
|
randomNum -- ; // برو داخل این همینطوری کمش کن
|
|
if (randomNum == 0){ // وقتی 0 شد
|
|
gameboard[i][j].color = 'W'; // اون خونه رو رنگ کن و اطرافش رو هم بررسی کن
|
|
checkSurround(i , j);
|
|
turn = !turn; // نوبت رو هم یادت نره برگردونی
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
}
|
|
|
|
void letsPlay(){
|
|
|
|
justPrint(); // اولش زمین رو نشون بده
|
|
|
|
while (true){ // این حلقه رو تا زمانی ادامه بده که بازی ادامه داره بعدش بریک میخوره خودش
|
|
|
|
|
|
for (int i = 0 ; i < gamesize ; i++){
|
|
for (int j = 0 ; j < gamesize ; j++){
|
|
checkPossible(i , j);
|
|
}
|
|
}
|
|
countPossible();
|
|
|
|
// بررسی کن ببین جایی هست که بزاری یا نه
|
|
|
|
if(numberOfPossible > 0){
|
|
if (singlemood && (turn == false)){ // اینجا حالتیه که سینگلیم و نوبت رباته
|
|
robatMove();
|
|
}
|
|
else{
|
|
move(); // اینم نوبت ادمه
|
|
}
|
|
|
|
}
|
|
else if (!finish()){ // اگه پر نشده بود و تو یه نوبت نتونستیم کاری کنیم میریم نوبت بعد
|
|
system("cls");
|
|
cout << "PASS!" << endl;
|
|
printMap();
|
|
getch();
|
|
turn = !turn;
|
|
numberOfPossible = 0 ;
|
|
clearPossible();
|
|
for (int i = 0 ; i < gamesize ; i++){
|
|
for (int j = 0 ; j < gamesize ; j++){
|
|
checkPossible(i , j);
|
|
}
|
|
}
|
|
countPossible();
|
|
if (numberOfPossible == 0){ // اگه تو نوبت بعدی هم نتونستیم کاری کنیم بازی تمومه
|
|
system("cls");
|
|
justPrint();
|
|
cout << "Game Finished" << endl;
|
|
result();
|
|
getch();
|
|
break;
|
|
}
|
|
else{
|
|
if (singlemood && (turn == false)){ // ولی اگه میشد کاری کنیم ادامه میدیم
|
|
robatMove();
|
|
}
|
|
else{
|
|
move();
|
|
}
|
|
|
|
}
|
|
}
|
|
else{ // اگه هم تابع فینیش تموم شده بود که یعنی زمین پره و بازی تامام شده
|
|
system("cls");
|
|
justPrint();
|
|
cout << "Game Finished" << endl;
|
|
result();
|
|
getch();
|
|
break ;
|
|
}
|
|
|
|
numberOfPossible = 0 ;
|
|
|
|
clearPossible();
|
|
|
|
|
|
}
|
|
|
|
singlemood = false ; // اینم غیرفعال میکنیم که برای دفعات بعدی مشکلی ایجاد نکنه این
|
|
}
|
|
|
|
void checkPossible(int i , int j){
|
|
if (gameboard[i][j].color == '0'){ // اولین شرظش اینه که خالی باشه
|
|
if (turn){ // با توجه به نوبت و رنگ باید بررسی شه
|
|
if(j+1 < gamesize){ //جهت راست رو توضیح میدم بقیه هم مثل همینه
|
|
if (gameboard[i][j+1].color == 'W'){ // اگه جهت راست داشتیم و سفید بود
|
|
for (int k = 2 ; j+k < gamesize ; k++){ // ادامه میدیم اگه به خونه خالی رسیدیم که هیچی
|
|
if(gameboard[i][j+k].color == '0'){
|
|
break;
|
|
}
|
|
if(gameboard[i][j+k].color == 'B'){ // اما اگه به مهره خودی (سیاه ) رسیدیم یعنی میتونیم محاصره کنیم پس مطلوبه
|
|
gameboard[i][j].possible = true; // اینو درست میکنیم
|
|
return; // و از حلقه میاییم بیرون
|
|
|
|
} // اگه سفید هم باشه بازم ادامه میده تا یا به سیاه برسه یا به 0
|
|
}
|
|
}
|
|
}
|
|
|
|
if (j-1 >= 0){
|
|
if (gameboard[i][j-1].color == 'W'){
|
|
for (int k = 2 ; j-k >= 0 ; k++){
|
|
if(gameboard[i][j-k].color == '0'){
|
|
break;
|
|
}
|
|
if(gameboard[i][j-k].color == 'B'){
|
|
gameboard[i][j].possible = true;
|
|
return;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i-1 >= 0){
|
|
if (gameboard[i-1][j].color == 'W'){
|
|
for (int k = 2 ; i-k >= 0 ; k++){
|
|
if(gameboard[i-k][j].color == '0'){
|
|
break;
|
|
}
|
|
if(gameboard[i-k][j].color == 'B'){
|
|
gameboard[i][j].possible = true;
|
|
return;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i+1 < gamesize ){
|
|
if (gameboard[i+1][j].color == 'W'){
|
|
for (int k = 2 ; i+k < gamesize ; k++){
|
|
if(gameboard[i+k][j].color == '0'){
|
|
break;
|
|
}
|
|
if(gameboard[i+k][j].color == 'B'){
|
|
gameboard[i][j].possible = true;
|
|
return;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i-1 >= 0 && j-1 >= 0){
|
|
if (gameboard[i-1][j-1].color == 'W'){
|
|
for (int k = 2 ; i-k >= 0 && j-k >= 0 ; k++){
|
|
if(gameboard[i-k][j-k].color == '0'){
|
|
break;
|
|
}
|
|
if(gameboard[i-k][j-k].color == 'B'){
|
|
gameboard[i][j].possible = true;
|
|
return;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i-1 >= 0 && j+1 < gamesize){
|
|
if (gameboard[i-1][j+1].color == 'W'){
|
|
for (int k = 2 ; i-k >= 0 && j+k < gamesize ; k++){
|
|
if(gameboard[i-k][j+k].color == '0'){
|
|
break;
|
|
}
|
|
if(gameboard[i-k][j+k].color == 'B'){
|
|
gameboard[i][j].possible = true;
|
|
return;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i+1 < gamesize && j-1 >= 0){
|
|
if (gameboard[i+1][j-1].color == 'W'){
|
|
for (int k = 2 ; i+k < gamesize && j-k >= 0 ; k++){
|
|
if(gameboard[i+k][j-k].color == '0'){
|
|
break;
|
|
}
|
|
if(gameboard[i+k][j-k].color == 'B'){
|
|
gameboard[i][j].possible = true;
|
|
return;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i+1 < gamesize && j+1 < gamesize){
|
|
if (gameboard[i+1][j+1].color == 'W'){
|
|
for (int k = 2 ; i+k < gamesize && j+k < gamesize ; k++){
|
|
if(gameboard[i+k][j+k].color == '0'){
|
|
break;
|
|
}
|
|
if(gameboard[i+k][j+k].color == 'B'){
|
|
gameboard[i][j].possible = true;
|
|
return;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
}
|
|
else{
|
|
|
|
if(j+1 < gamesize){
|
|
if (gameboard[i][j+1].color == 'B'){
|
|
for (int k = 2 ; j+k < gamesize ; k++){
|
|
if(gameboard[i][j+k].color == '0'){
|
|
break;
|
|
}
|
|
if(gameboard[i][j+k].color == 'W'){
|
|
gameboard[i][j].possible = true;
|
|
return;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
if (j-1 >= 0){
|
|
if (gameboard[i][j-1].color == 'B'){
|
|
for (int k = 2 ; j-k >= 0 ; k++){
|
|
if(gameboard[i][j-k].color == '0'){
|
|
break;
|
|
}
|
|
if(gameboard[i][j-k].color == 'W'){
|
|
gameboard[i][j].possible = true;
|
|
return;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i-1 >= 0){
|
|
if (gameboard[i-1][j].color == 'B'){
|
|
for (int k = 2 ; i-k >= 0 ; k++){
|
|
if(gameboard[i-k][j].color == '0'){
|
|
break;
|
|
}
|
|
if(gameboard[i-k][j].color == 'W'){
|
|
gameboard[i][j].possible = true;
|
|
return;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i+1 < gamesize ){
|
|
if (gameboard[i+1][j].color == 'B'){
|
|
for (int k = 2 ; i+k < gamesize ; k++){
|
|
if(gameboard[i+k][j].color == '0'){
|
|
break;
|
|
}
|
|
if(gameboard[i+k][j].color == 'W'){
|
|
gameboard[i][j].possible = true;
|
|
return;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i-1 >= 0 && j-1 >= 0){
|
|
if (gameboard[i-1][j-1].color == 'B'){
|
|
for (int k = 2 ; i-k >= 0 && j-k >= 0 ; k++){
|
|
if(gameboard[i-k][j-k].color == '0'){
|
|
break;
|
|
}
|
|
if(gameboard[i-k][j-k].color == 'W'){
|
|
gameboard[i][j].possible = true;
|
|
return;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i-1 >= 0 && j+1 < gamesize){
|
|
if (gameboard[i-1][j+1].color == 'B'){
|
|
for (int k = 2 ; i-k >= 0 && j+k < gamesize ; k++){
|
|
if(gameboard[i-k][j+k].color == '0'){
|
|
break;
|
|
}
|
|
if(gameboard[i-k][j+k].color == 'W'){
|
|
gameboard[i][j].possible = true;
|
|
return;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i+1 < gamesize && j-1 >= 0){
|
|
if (gameboard[i+1][j-1].color == 'B'){
|
|
for (int k = 2 ; i+k < gamesize && j-k >= 0 ; k++){
|
|
if(gameboard[i+k][j-k].color == '0'){
|
|
break;
|
|
}
|
|
if(gameboard[i+k][j-k].color == 'W'){
|
|
gameboard[i][j].possible = true;
|
|
return;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i+1 < gamesize && j+1 < gamesize){
|
|
if (gameboard[i+1][j+1].color == 'B'){
|
|
for (int k = 2 ; i+k < gamesize && j+k < gamesize ; k++){
|
|
if(gameboard[i+k][j+k].color == '0'){
|
|
break;
|
|
}
|
|
if(gameboard[i+k][j+k].color == 'W'){
|
|
gameboard[i][j].possible = true;
|
|
return;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
}
|
|
|
|
}
|
|
}
|
|
|
|
|
|
void clearPossible(){
|
|
for (int i = 0 ; i < gamesize ; i++){
|
|
for (int j = 0 ; j < gamesize ; j++){
|
|
gameboard[i][j].possible= false; // همه رو ری استارت میکنه برای بررسی مجدد
|
|
}
|
|
}
|
|
}
|
|
|
|
void checkSurround(int i , int j){ // i , j محل قرار گیری مهره جدید که با cusor i j برابره
|
|
if (turn){ // با توجه به نوبت برمیگردونیم
|
|
// باید حداقل 2 تا اونور ترش وجود داشته باشه
|
|
if (j+2 < gamesize){ // برگردوندن در جهت راست
|
|
for (int k = 1 ; k+j < gamesize ; k++){
|
|
if (gameboard[i][j+k].color == 'W'){ // فعلا اگه سفید بود ادامه میدیم تا برسیم به مشکی دوم
|
|
continue;
|
|
}
|
|
if (gameboard[i][j+k].color == 'B'){ // خوب رسیدیم به مشکی دوم حالا باید برگردیم تا مشکی اول و وسط رو سفید کنیم
|
|
int t = k ;
|
|
while(t > 1){
|
|
gameboard[i][j+t-1].color = 'B'; // دوباره به اندازه کا برمیگردیم و سفیدا رو سیاه میکنیم
|
|
t--;
|
|
}
|
|
break;
|
|
}
|
|
if (gameboard[i][j+k].color=='0'){ // اگه هم به 0 رسیدیم این وسط یعنی زدیم جاده خاکی و حلقه رو بشکون بیا بیرون
|
|
break;
|
|
|
|
}
|
|
} // برای بقیه جهت ها هم همینه که توضیح نمیدم
|
|
}
|
|
|
|
if (j-2 >= 0 ){ // برگردوندن در جهت چپ
|
|
for (int k = 1 ; j-k >= 0 ; k++){
|
|
if (gameboard[i][j-k].color == 'W'){
|
|
continue;
|
|
}
|
|
if (gameboard[i][j-k].color == 'B'){
|
|
int t = k ;
|
|
while(t > 1){
|
|
gameboard[i][j-t+1].color = 'B';
|
|
t--;
|
|
}
|
|
break;
|
|
}
|
|
if (gameboard[i][j-k].color=='0'){
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i-2 >= 0 ){ // برگردوندن در جهت بالا
|
|
for (int k = 1 ; i-k >= 0 ; k++){
|
|
if (gameboard[i-k][j].color == 'W'){
|
|
continue;
|
|
}
|
|
if (gameboard[i-k][j].color == 'B'){
|
|
int t = k ;
|
|
while(t > 1){
|
|
gameboard[i-t+1][j].color = 'B';
|
|
t--;
|
|
}
|
|
break;
|
|
}
|
|
if (gameboard[i-k][j].color=='0'){
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i+2 < gamesize){ // برگردوندن در جهت پایین
|
|
for (int k = 1 ; k+i < gamesize ; k++){
|
|
if (gameboard[i+k][j].color == 'W'){
|
|
continue;
|
|
}
|
|
if (gameboard[i+k][j].color == 'B'){
|
|
int t = k ;
|
|
while(t > 1){
|
|
gameboard[i+t-1][j].color = 'B';
|
|
t--;
|
|
}
|
|
break;
|
|
}
|
|
if (gameboard[i+k][j].color=='0'){
|
|
break;
|
|
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i-2 >= 0 && j-2 >= 0 ){
|
|
for (int k = 1 ; i-k >= 0 && j-k >= 0 ; k++){
|
|
if(gameboard[i-k][j-k].color == '0'){
|
|
break;
|
|
}
|
|
if (gameboard[i-k][j-k].color == 'B'){
|
|
int t = k ;
|
|
while(t>1){
|
|
gameboard[i-t+1][j-t+1].color = 'B';
|
|
t--;
|
|
}
|
|
break;
|
|
}
|
|
if(gameboard[i-k][j-k].color == 'W'){
|
|
continue;
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i-2 >= 0 && j+2 < gamesize ){
|
|
for (int k = 1 ; i-k >= 0 && j+k < gamesize ; k++){
|
|
if(gameboard[i-k][j+k].color == '0'){
|
|
break;
|
|
}
|
|
if (gameboard[i-k][j+k].color == 'B'){
|
|
int t= k ;
|
|
while(t>1){
|
|
gameboard[i-t+1][j+t-1].color = 'B';
|
|
t--;
|
|
}
|
|
break;
|
|
}
|
|
if(gameboard[i-k][j+k].color == 'W'){
|
|
continue;
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i+2 < gamesize && j-2 >= 0 ){
|
|
for (int k = 1 ; i+k < gamesize && j-k >= 0 ; k++){
|
|
if(gameboard[i+k][j-k].color == '0'){
|
|
break;
|
|
}
|
|
if (gameboard[i+k][j-k].color == 'B'){
|
|
int t = k ;
|
|
while(t>1){
|
|
gameboard[i+t-1][j-t+1].color = 'B';
|
|
t--;
|
|
}
|
|
break;
|
|
}
|
|
if(gameboard[i+k][j-k].color == 'W'){
|
|
continue;
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i+2 < gamesize && j+2 < gamesize ){
|
|
for (int k = 1 ; i+k < gamesize && j+k < gamesize ; k++){
|
|
if(gameboard[i+k][j+k].color == '0'){
|
|
break;
|
|
}
|
|
if (gameboard[i+k][j+k].color == 'B'){
|
|
int t = k;
|
|
while(t>1){
|
|
gameboard[i+t-1][j+t-1].color = 'B';
|
|
t--;
|
|
}
|
|
break;
|
|
}
|
|
if(gameboard[i+k][j+k].color == 'W'){
|
|
continue;
|
|
}
|
|
}
|
|
}
|
|
|
|
}
|
|
else {
|
|
|
|
if (j+2 < gamesize){ // برگردوندن در جهت راست
|
|
for (int k = 1 ; k+j < gamesize ; k++){
|
|
if (gameboard[i][j+k].color == 'B'){
|
|
continue;
|
|
}
|
|
if (gameboard[i][j+k].color == 'W'){
|
|
int t = k ;
|
|
while(t > 1){
|
|
gameboard[i][j+t-1].color = 'W';
|
|
t--;
|
|
}
|
|
break;
|
|
}
|
|
if (gameboard[i][j+k].color=='0'){
|
|
break;
|
|
|
|
}
|
|
}
|
|
}
|
|
|
|
if (j-2 >= 0 ){ // برگردوندن در جهت چپ
|
|
for (int k = 1 ; j-k >= 0 ; k++){
|
|
if (gameboard[i][j-k].color == 'B'){
|
|
continue;
|
|
}
|
|
if (gameboard[i][j-k].color == 'W'){
|
|
int t = k ;
|
|
while(t > 1){
|
|
gameboard[i][j-t+1].color = 'W';
|
|
t--;
|
|
}
|
|
break;
|
|
}
|
|
if (gameboard[i][j-k].color=='0'){
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i-2 >= 0 ){ // برگردوندن در جهت بالا
|
|
for (int k = 1 ; i-k >= 0 ; k++){
|
|
if (gameboard[i-k][j].color == 'B'){
|
|
continue;
|
|
}
|
|
if (gameboard[i-k][j].color == 'W'){
|
|
int t = k ;
|
|
while(t > 1){
|
|
gameboard[i-t+1][j].color = 'W';
|
|
t--;
|
|
}
|
|
break;
|
|
}
|
|
if (gameboard[i-k][j].color=='0'){
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i+2 < gamesize){ // برگردوندن در جهت پایین
|
|
for (int k = 1 ; k+i < gamesize ; k++){
|
|
if (gameboard[i+k][j].color == 'B'){
|
|
continue;
|
|
}
|
|
if (gameboard[i+k][j].color == 'W'){
|
|
int t = k ;
|
|
while(t > 1){
|
|
gameboard[i+t-1][j].color = 'W';
|
|
t--;
|
|
}
|
|
break;
|
|
}
|
|
if (gameboard[i+k][j].color=='0'){
|
|
break;
|
|
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i-2 >= 0 && j-2 >= 0 ){
|
|
for (int k = 1 ; i-k >= 0 && j-k >= 0 ; k++){
|
|
if(gameboard[i-k][j-k].color == '0'){
|
|
break;
|
|
}
|
|
if (gameboard[i-k][j-k].color == 'W'){
|
|
int t = k ;
|
|
while(t>1){
|
|
gameboard[i-t+1][j-t+1].color = 'W';
|
|
t--;
|
|
}
|
|
break;
|
|
}
|
|
if(gameboard[i-k][j-k].color == 'B'){
|
|
continue;
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i-2 >= 0 && j+2 < gamesize ){
|
|
for (int k = 1 ; i-k >= 0 && j+k < gamesize ; k++){
|
|
if(gameboard[i-k][j+k].color == '0'){
|
|
break;
|
|
}
|
|
if (gameboard[i-k][j+k].color == 'W'){
|
|
int t = k ;
|
|
while(t>1){
|
|
gameboard[i-t+1][j+t-1].color = 'W';
|
|
t--;
|
|
}
|
|
break;
|
|
}
|
|
if(gameboard[i-k][j+k].color == 'B'){
|
|
continue;
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i+2 < gamesize && j-2 >= 0 ){
|
|
for (int k = 1 ; i+k < gamesize && j-k >= 0 ; k++){
|
|
if(gameboard[i+k][j-k].color == '0'){
|
|
break;
|
|
}
|
|
if (gameboard[i+k][j-k].color == 'W'){
|
|
int t= k ;
|
|
while(t>1){
|
|
gameboard[i+t-1][j-t+1].color = 'W';
|
|
t--;
|
|
}
|
|
break;
|
|
}
|
|
if(gameboard[i+k][j-k].color == 'B'){
|
|
continue;
|
|
}
|
|
}
|
|
}
|
|
|
|
if (i+2 < gamesize && j+2 < gamesize ){
|
|
for (int k = 1 ; i+k < gamesize && j+k < gamesize ; k++){
|
|
if(gameboard[i+k][j+k].color == '0'){
|
|
break;
|
|
}
|
|
if (gameboard[i+k][j+k].color == 'W'){
|
|
int t = k ;
|
|
while(t>1){
|
|
gameboard[i+t-1][j+t-1].color = 'W';
|
|
t--;
|
|
}
|
|
break;
|
|
}
|
|
if(gameboard[i+k][j+k].color == 'B'){
|
|
continue;
|
|
}
|
|
}
|
|
}
|
|
|
|
}
|
|
}
|
|
|
|
void countPossible(){
|
|
numberOfPossible = 0;
|
|
for(int i = 0 ; i < gamesize ; i++){
|
|
for (int j = 0 ; j < gamesize ; j++){
|
|
if (gameboard[i][j].possible == true) numberOfPossible++; // هر تعداد که میشه توش خونه بزاریم رو میشماره دیگه
|
|
}
|
|
}
|
|
}
|
|
|
|
void justPrint(){
|
|
cout << "┌";
|
|
for (int a = 2*gamesize +1 ; a > 0 ; a--){
|
|
cout << "─";
|
|
}
|
|
cout << "┐" << endl ;
|
|
|
|
for(int i = 0 ; i < gamesize ; i++){
|
|
cout << "│ ";
|
|
for (int j = 0 ; j < gamesize ; j++){
|
|
if (gameboard[i][j].color == 'W') cout << "■" << " ";
|
|
else if (gameboard[i][j].color == 'B') cout << "□" << " ";
|
|
else if (gameboard[i][j].color == '0') cout << "." << " ";
|
|
}
|
|
cout << "│"<< endl;
|
|
}
|
|
|
|
cout << "└";
|
|
for (int a = 2*gamesize +1 ; a > 0 ; a--){
|
|
cout << "─";
|
|
}
|
|
cout << "┘" << endl ;
|
|
|
|
}
|
|
|
|
void countscore(){
|
|
Player1.score = 0 ; // از قبل ممکنه توش چیزی باشه 0 کن اشتب نشه
|
|
Player2.score = 0 ;
|
|
|
|
for(int i = 0 ; i < gamesize ; i++){
|
|
for (int j = 0 ; j < gamesize ; j++){
|
|
if (gameboard[i][j].color == 'B') Player1.score ++ ; // بشمار ببین چند تا داریم از هر کدوم
|
|
else if (gameboard[i][j].color == 'W') Player2.score++;
|
|
}
|
|
}
|
|
}
|
|
|
|
void result (){
|
|
|
|
countscore();
|
|
|
|
ofstream historyfile("GameHistory.txt" , ios::app); // این فایل رو باز کن که اطلاعات باز یور بریزیم توش
|
|
|
|
if (historyfile.is_open()){
|
|
historyfile << "------------------------------------" << endl ;
|
|
historyfile << "Player1 name :" << Player1.name << endl;
|
|
historyfile << "Player2 name :" << Player2.name << endl;
|
|
historyfile << "Gamesize :" << gamesize << endl ;
|
|
}
|
|
|
|
if (Player1.score > Player2.score){ // اگه بازیکن 1 برنده بود اینا
|
|
cout << Player1.name << " win !" << endl ;
|
|
if (historyfile.is_open()){
|
|
historyfile << Player1.name << " win !" << endl ;
|
|
historyfile << Player1.name << " scores :" << Player1.score << endl ;
|
|
historyfile << Player2.name << " scores :" << Player2.score << endl ;
|
|
}
|
|
}
|
|
|
|
else if (Player1.score < Player2.score){ // اگه بازیکن 2 برنده بود اینا
|
|
cout << Player2.name << " win !" << endl ;
|
|
if (historyfile.is_open()){
|
|
historyfile << Player2.name << " win !" << endl ;
|
|
historyfile << Player1.name << " scores :" << Player1.score << endl ;
|
|
historyfile << Player2.name << " scores :" << Player2.score << endl ;
|
|
}
|
|
}
|
|
|
|
else { // اگه هم مساوی شد اینا رو بنویس تو فایل
|
|
cout << " DRAW !" << endl ;
|
|
if (historyfile.is_open()){
|
|
historyfile << " Draw !" << endl ;
|
|
historyfile << Player1.name << " scores :" << Player1.score << endl ;
|
|
historyfile << Player2.name << " scores :" << Player2.score << endl ;
|
|
}
|
|
|
|
}
|
|
|
|
cout << Player1.name << " scores :" << Player1.score << endl ; // در نهایت اینا رو تو ترمینال بازی نشون بده
|
|
cout << Player2.name << " scores :" << Player2.score << endl ;
|
|
|
|
historyfile << "Time of game : " << getDateTime() << endl ;
|
|
|
|
|
|
|
|
historyfile.close(); // فایل رو هم ببند بره پی کارش
|
|
|
|
}
|
|
|
|
void printMap(){
|
|
if (turn){ // اینجا نوبت رو درج میکنیم
|
|
if (numberOfPossible !=0){
|
|
cout << Player1.name << " turn :" << endl << endl;
|
|
}
|
|
}
|
|
else{
|
|
if (numberOfPossible != 0){
|
|
cout << Player2.name << " turn :" << endl << endl;
|
|
}
|
|
}
|
|
|
|
countscore();
|
|
|
|
cout << Player1.name << " Score:" << Player1.score << endl ;
|
|
cout << Player2.name << " Score:" << Player2.score << endl << endl << "┌" ;
|
|
|
|
for (int a = 2*gamesize +1 ; a > 0 ; a--){
|
|
cout << "─";
|
|
}
|
|
cout << "┐" << endl ;
|
|
|
|
|
|
for (int i = 0 ; i < gamesize ; i++){
|
|
cout << "│ " ;
|
|
for (int j = 0 ; j <gamesize ; j++){
|
|
while(cursor_i <0){ // مشابه اینو توخط 215 توضیح دادم
|
|
cursor_i = cursor_i + gamesize;
|
|
}
|
|
while(cursor_j <0){
|
|
cursor_j = cursor_j + gamesize;
|
|
}
|
|
if (cursor_i >= gamesize){
|
|
cursor_i = cursor_i % gamesize;
|
|
}
|
|
if(cursor_j >= gamesize){
|
|
cursor_j = cursor_j % gamesize ;
|
|
}
|
|
if ( i == (cursor_i % gamesize) && j == (cursor_j % gamesize)){ // که به جای کرسر ایکس رو نشون بده
|
|
cout << "x " ;
|
|
}
|
|
else{
|
|
if (gameboard[i][j].possible == true){ // اگه امکانش بود + بزار
|
|
cout << "+ ";
|
|
}
|
|
else {
|
|
if (gameboard[i][j].color == 'W') cout << "■" << " ";
|
|
else if (gameboard[i][j].color == 'B') cout << "□" << " ";
|
|
else if (gameboard[i][j].color == '0') cout << "." << " "; // اگه هم نه حرف مربوطه رو بزار با فاصله ها
|
|
}
|
|
|
|
|
|
}
|
|
}
|
|
cout << "│ "<< endl ;
|
|
}
|
|
|
|
cout << "└";
|
|
for (int a = 2*gamesize +1 ; a > 0 ; a--){
|
|
cout << "─";
|
|
}
|
|
cout << "┘" << endl ;
|
|
|
|
}
|
|
|
|
bool finish(){ // اگه هنوز خونه 0 داشته باشیم غلط برمیگردونه
|
|
for (int i = 0 ; i < gamesize ; i++){
|
|
for(int j = 0 ; j < gamesize ; j++){
|
|
if(gameboard[i][j].color == '0') return false;
|
|
}
|
|
}
|
|
return true; // اگه هم همه اش پر شده بود درست رو میده
|
|
}
|
|
|
|
|
|
// راستش این تابع بعدی رو هم از هوش مصنوعی گرفتم خودمم دقیقا نمیدونم چطوری کار میکنه
|
|
|
|
|
|
string getDateTime() {
|
|
time_t now = time(0); // گرفتن زمان فعلی
|
|
tm *ltm = localtime(&now); // تبدیل به زمان محلی
|
|
char buffer[100];
|
|
strftime(buffer, sizeof(buffer), "%Y-%m-%d %H:%M:%S", ltm);
|
|
return string(buffer); // خروجی به صورت رشته
|
|
}
|
|
|
|
|
|
|
|
|
|
void cleanIt(){
|
|
for (int i = 0 ; i <gamesize ; i++){ // اینم پاک میکنه چیزایی که داریم رو از حافطه heap
|
|
delete [] gameboard[i];
|
|
}
|
|
delete [] gameboard;
|
|
}
|