• (3 Pages)
  • +
  • 1
  • 2
  • 3

Chess Board and Moving Pieces in C++ How to make a simple chess program Rate Topic: ***** 2 Votes

#16 dr.tiberius  Icon User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 14
  • Joined: 23-February 10

Posted 25 February 2010 - 05:32 PM

Very nice tutorial .
Was This Post Helpful? 0
  • +
  • -

#17 PlasticineGuy  Icon User is offline

  • mov dword[esp+eax],0
  • member icon

Reputation: 281
  • View blog
  • Posts: 1,436
  • Joined: 03-January 10

Posted 01 March 2010 - 02:27 AM

Solution for all your issues with Dev-C++: Stop using such an old IDE.
Was This Post Helpful? -1
  • +
  • -

#18 Guest_Tyr*


Reputation:

Posted 01 April 2010 - 08:39 AM

When will part 2 be posted?
Was This Post Helpful? 0

#19 Deepglue555  Icon User is offline

  • D.I.C Head
  • member icon

Reputation: 6
  • View blog
  • Posts: 117
  • Joined: 13-April 09

Posted 28 June 2012 - 09:07 AM

View PostTyr, on 01 April 2010 - 09:39 AM, said:

When will part 2 be posted?



Wow, I forgot entirely about a part 2 for ages.

The good news is I have the Visual Basic 6.0 code for a full working chess program all legal rules including the intricate ones, all written by me years ago and documented in a youtube video I made of it.

Also good news, I ported it all to C++, working and everything..

Slightly bad news is I never commented any of my code (bad programming practise .. I know ..).

However now I can put it on my to do list, 1.) To comment the code, 2.) To make it a tutorial for here 3.) to port it to Microsoft Visual C++. (From Borland C++ 6).

The bad is news is I will be doing thousands of computer science students homework for ages.. and they might not really learn how to improvise code the way I did, but they can still learn from the comments and tutorial providing I finish that. I did not program this chess player for optimized speed, but rather than passing arrays of integers or doubles I used strings to be passed and received between functions. (Strings are generally slower).

However it does the job and plays 99.x% legal moves. (The game of chess has lots of legalities to take into consideration such as 'en passant' and the 50 move rule, all of which I programmed into the programs rule deductions when a human or computer moves). I didn't however program the more intricate rules into the AI or computer past the first ply.

Programming a computer to detect legal and illegal moves even not including the en passant and other rules but just piece movements is monotonous and tedious kinda boring, however commenting it wont be as much. But there is alot of code and I'm not sure what time frame I might do it in or when I might start that.

I will put it on my todo list to A.) Port the working code from Borland to the latest Microsoft Visual C++ (Win32 console). B.) comment the code C.) Create the tutorial for those interested here.

And/or do the same for the Visual Basic 6.0 version but just commenting the code and making the tutorial.

(I had tried the automatic converter for VB6 to VB.net and it failed and even destroyed the current version of the source code I had for it and had to revert to a slightly inferior source code i had backed up for it [years ago btw]).

Also the AI/Engine needs a complete rework, the harder I worked at making it more intelligent and adding pruning the dumber and crazier it got (after a certain point).

...

I will update you when I attempt to start this.
Was This Post Helpful? 0
  • +
  • -

#20 Deepglue555  Icon User is offline

  • D.I.C Head
  • member icon

Reputation: 6
  • View blog
  • Posts: 117
  • Joined: 13-April 09

Posted 28 June 2012 - 10:44 AM

Ok, I took a look at the C++ source code and it is huge, 2471 lines of code. And I didn't even port the engine to the C++ code.

Commenting all of that might be a mid sized book worth of information. Not sure it's a tutorial the readers would just get through in a day or two.

Also I coded the UCI protocol into it, enough to play a human by the 'computer' choosing any randomly chosen legal move.

This might be too long for a tutorial I guess, is there another classification I would use for it if I did it as a tutorial?

The VB6 version is about 6800 lines of code but alot of that is GUI parameters and stuff that VB6 injects to tell the visual stuff where to place and how to work.

I might have to write a dumbed down version of just legal moves for the pieces and take king in check legal moves into consideration.
Was This Post Helpful? 0
  • +
  • -

#21 snoopy11  Icon User is offline

  • Engineering ● Software
  • member icon

Reputation: 780
  • View blog
  • Posts: 2,312
  • Joined: 20-March 10

Posted 29 June 2012 - 01:44 PM

You can just

Split the Tutorial into parts if it is too large

If it is 6000-7000 lines of code consider
splitting it into 6 parts.

Best Wishes

Snoopy.
Was This Post Helpful? 0
  • +
  • -

#22 vincent_dk  Icon User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 1
  • Joined: 05-July 12

Posted 05 July 2012 - 05:10 AM

Thank for share, i need it! :bananaman:
Was This Post Helpful? 0
  • +
  • -

#23 gopal1432  Icon User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 2
  • Joined: 12-September 12

Posted 12 September 2012 - 09:57 PM

[quote name='Deepglue555' date='11 May 2009 - 02:04 AM' timestamp='1242032669' post='637420']
[code]
#include<iostream>
#include<string>
#include<stdlib>


// in this example pieces aer described as integer values
// we will make them constants, so that if at any time we want to change their values we can do so here
// but will still need to recompile

const int pawn = 100;
const int bishop = 305;
const int knight = 300;
const int rook = 500;
const int queen = 900;
const int king = 2000;

  • why are you using const int pawn=100;
  • how you can indicate the 100 to pawn

Attached File(s)


Was This Post Helpful? 0
  • +
  • -

#24 Namshum  Icon User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 3
  • Joined: 18-October 12

Posted 18 October 2012 - 01:20 AM

Hi! Deepglue555 when will you finish the 2nd part of Simple Chess
Was This Post Helpful? 0
  • +
  • -

#25 modi123_1  Icon User is online

  • Suitor #2
  • member icon



Reputation: 9223
  • View blog
  • Posts: 34,630
  • Joined: 12-June 08

Posted 18 October 2012 - 06:59 AM

The tutorial was posted 11 May 2009.

The OP hasn't been on since August. It might be a while.
Was This Post Helpful? 0
  • +
  • -

#26 Namshum  Icon User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 3
  • Joined: 18-October 12

Posted 18 October 2012 - 11:09 PM

Hi #25 modi123_1 Can you suggest a move generator on the basis of the code of deepglue555
Was This Post Helpful? 0
  • +
  • -

#27 modi123_1  Icon User is online

  • Suitor #2
  • member icon



Reputation: 9223
  • View blog
  • Posts: 34,630
  • Joined: 12-June 08

Posted 19 October 2012 - 07:03 AM

No.
Was This Post Helpful? 0
  • +
  • -

#28 Namshum  Icon User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 3
  • Joined: 18-October 12

Posted 20 October 2012 - 12:55 AM

Thanks!
Was This Post Helpful? 0
  • +
  • -

#29 Deepglue555  Icon User is offline

  • D.I.C Head
  • member icon

Reputation: 6
  • View blog
  • Posts: 117
  • Joined: 13-April 09

Posted 01 August 2014 - 03:14 PM

I just posted a new tutorial for a UCI chess engine written in c++, the code is there to generate all legal moves of chess including special moves like castling, en passant, promotions and underpromotions. The version I just posted is a random mover and does not play any illegal chess moves, and as far as I can tell generates a full move list for any position or game posed to it.

It has a skeleton of the UCI protocol, enough to work as a random mover against itself or other chess engines. You can play against it by loading it in Arena chess interface (free).

Hopefully it will be approved soon....
Was This Post Helpful? 0
  • +
  • -

#30 Deepglue555  Icon User is offline

  • D.I.C Head
  • member icon

Reputation: 6
  • View blog
  • Posts: 117
  • Joined: 13-April 09

Posted 06 August 2014 - 09:40 PM

View PostNamshum, on 19 October 2012 - 07:09 AM, said:

Hi #25 modi123_1 Can you suggest a move generator on the basis of the code of deepglue555


Here is some code for the piece move generation:

string whitemoves(void){	//generate all move coordinates in fromSQa/b and toSQa/b (arrays up to 218 possible moves maximum in a legal chess position)
	string allmoves;
	int fromSQa[218];
	int fromSQb[218];
	int toSQa[218];
	int toSQb[218];
	
	int a = 0;
	int b = 0;
	int c = 0;
	int d = 0;
	int e = 0;
	int f = 0;
	int z = 0;
		

	for (a = 0; a < 8; a++){
		for (b = 0; b < 8; b++){
			switch (board[a][b]) {
			
				case queen:
					{
						for (e = -1; e <= 1; e++) {
						for (f = -1; f <= 1; f++) {
							c = a + e;
							d = b + f;
							if (!(f == 0 && e == 0)) { // process  the following code provided f and e are not both 0
								do {
									if (bounds(c, d)) {
										
										if (board[c][d] == 0) {
											fromSQa[z] = a;
											fromSQb[z] = b;
											toSQa[z] = c;
											toSQb[z] = d;
											z++;
										}
										if (board[c][d] < 0) {
											fromSQa[z] = a;
											fromSQb[z] = b;
											toSQa[z] = c;
											toSQb[z] = d;

											z++;
											break; 
										}
										if (board[c][d] > 0) break; 
										c = c + e;
										d = d + f;
									}
								}
								while (!(bounds(c, d) == false));
							
							}
							
						}
					}

				break;
				case rook:
					for (e = -1; e <= 1; e++) {
						for (f = -1; f <= 1; f++) {
							c = a + e;
							d = b + f;
							if (abs(e)+abs(f) == 1) {
								do {
									if (bounds(c, d)) {
										
										if (board[c][d] == 0) {
											fromSQa[z] = a;
											fromSQb[z] = b;
											toSQa[z] = c;
											toSQb[z] = d;
											z++;
										}
										if (board[c][d] < 0) {
											fromSQa[z] = a;
											fromSQb[z] = b;
											toSQa[z] = c;
											toSQb[z] = d;

											z++;
											break; 
										}
										if (board[c][d] > 0) break; 
										c = c + e;
										d = d + f;
									}
								}
								while (!(bounds(c, d) == false));
							
							}
							
						}
					}
					break;
					case bishop:
					for (e = -1; e <= 1; e++) {
						for (f = -1; f <= 1; f++) {
							c = a + e;
							d = b + f;
							if (abs(e)+abs(f) == 2) {
								do {
									if (bounds(c, d)) {
										
										if (board[c][d] == 0) {
											fromSQa[z] = a;
											fromSQb[z] = b;
											toSQa[z] = c;
											toSQb[z] = d;
											z++;
										}
									if (board[c][d] < 0) {
										fromSQa[z] = a;
										fromSQb[z] = b;
										toSQa[z] = c;
										toSQb[z] = d;

										z++;
										break; 
									}
									if (board[c][d] > 0) break; 

								}
							c = c + e;
							d = d + f;
							}
							while (!(bounds(c, d) == false));
						}
					}
				}
				break;
				case knight:
					for(e=-2; e<=2; e+=1){
						for(f=-2; f<=2; f+=1){
							c = a + e;
							d = b + f;
							if(abs(e) + abs(f) == 3){
								if(bounds(c,d)){
									if(board[c][d]<=0){
										fromSQa[z]=a;
										fromSQb[z]=b;
										toSQa[z]=c;
										toSQb[z]=d;
										z+=1;
									}
								}
							}
						}
					}
					break;
					case pawn:
						//white pawn attack left and forward
						c = a + 1;
						d = b - 1;
						if (bounds(c, d)) {		//bounds checks if the square is on the board, if not go to next move direction for pawn.
							
							if (board[c][d] < 0 || (epa == c && epb == d)) { //if diagonal square attacked contains a piece valued less than zero then capture is possible, or square is the en passant square from previous move.
								fromSQa[z] = a;
								fromSQb[z] = b;
								toSQa[z] = c;
								toSQb[z] = d;
								z++;
							}
						}
						//white pawn attack right and forward
						c = a + 1;
						d = b + 1;
						if (bounds(c, d)) {
							
							if (board[c][d] < 0 || (epa == c && epb == d)) {
								fromSQa[z] = a;
								fromSQb[z] = b;
								toSQa[z] = c;
								toSQb[z] = d;
								z++;
							}
						}
						//check if one square forward is unoccupied and add it to the movelist
							if (a == 1) {
								c = 2;
								d = b;
								if (bounds(c, d)) {
									
									if (board[c][d] == 0) {
										fromSQa[z] = a;
										fromSQb[z] = b;
										toSQa[z] = c;
										toSQb[z] = d;
										z++;
										c = 3;
										d = b;
										//another square forward if the pawn is on it's starting rank
										if (bounds(c, d)) {
											
											if (board[c][d] == 0) {
												fromSQa[z] = a;
												fromSQb[z] = b;
												toSQa[z] = c;
												toSQb[z] = d;
												z++;
											}
										}
									}
								}
							}
						else {	//pawn is not on starting rank
							c = a + 1;
							d = b;
							if (bounds(c, d)) {
								if (board[c][d] == 0) {
									fromSQa[z] = a;
									fromSQb[z] = b;
									toSQa[z] = c;
									toSQb[z] = d;
									z++;
								}
							}
						}

					break;
					case king:
						for (e = -1; e <= 1; e++) {
							for (f = -1; f <= 1; f++) {
								if (!(e == 0 && f == 0)) {
									c = a + e;
									d = b + f;

									if (bounds(c, d)) {		//checks if coordinates exist on the board
													  
										if (board[c][d] <= 0 && checkwhite(c, d, a, B)/>.empty()) {
											fromSQa[z] = a;
											fromSQb[z] = b;
											toSQa[z] = c;
											toSQb[z] = d;
											z++;
										}
									}
								}
							}
						}
					//castleKingSide
						if (wkside && a == 0 && b == 4 && board[0][7] == rook && board[0][6] == 0 && board[0][5] == 0) {
							if (checkwhite(0, 4, 0, 4).empty() && checkwhite(0, 5, 0, 4).empty() && checkwhite(0, 6, 0, 4).empty()) {
								fromSQa[z] = 0;
								fromSQb[z] = 4;
								toSQa[z] = 0;
								toSQb[z] = 6;
								z++;
							}
						}

						//castleQueenSide
						if (wqside == true && a == 0 && b == 4 && board[0][0] == rook && board[0][1] == 0 && board[0][2] == 0 && board[0][3] == 0) {
							if (checkwhite(0, 4, 0, 4).empty() && checkwhite(0, 3, 0, 4).empty() && checkwhite(0, 2, 0, 4).empty()) {
								fromSQa[z] = 0;
								fromSQb[z] = 4;
								toSQa[z] = 0;
								toSQb[z] = 2;
								z++;
							}
						}
				} 

			}// close switch


		}
/* after this you will want to return the information stored in fromSQa/b[] and toSQa/b[] to the int main of the program OR further filter out all moves that leave the white king in check thus being illegal moves in chess (you can't leave your own king in check after your move */

/* code here to either sort/filter moves or form them as a string of all moves or all legal moves to return from the function */

return allmoves;
}
	}



To start with we will need four containers for each move, so obviously we will need an array. Since 218 is the maximum possible moves from any given position in chess we will use that as an index.

	int fromSQa[218];
	int fromSQb[218];
	int toSQa[218];
	int toSQb[218];


each move has 4 coordinates, the from square rank (fromSQa[]), the from square file (fromSQb[]), the to square rank (toSQa[]), and the to square file (toSQb[]).

When inserting a move into those 4 arrays, we will index them with z, zwill start at 0, z = 0;, each time we deposit the coordinates into the 4 arrays we will need to immediately increment z by one so it is ready to recieve the next animal/piece move. z++; which is the same as z = z + 1;.


Here we declare all the important variables we will be using to calculate the animal piece moves:

	
	int a = 0;
	int b = 0;
	int c = 0;
	int d = 0;
	int e = 0;
	int f = 0;
	int z = 0;


z will be the index for the 4 arrays, a will contain the coordinate of the rank of the piece we are creating moves for, b will be the file of the piece we are generating moves for, c will be the rank of the square to move to, being tested, d will be the file of the 'move to' being tested, e will be how much to add to 'a' to get the next 'c' (rank), and f will be how much to add to b to get the next d (file). So e and f control the direction of the move, in case of rooks, bishops and queens it will be repeatedly added to get further moves in the same direction as long as empty squares are being processed and still on the board.

I hope you all still follow..

Now we must search every square on the board for whites pieces,

We do that with two for loops that both count 0-7 and one is contained in the other.

	
	for (a = 0; a < 8; a++){
		for (b = 0; b < 8; b++){

/* code in between */

		}
	}



The resulting pieces found at board[a][b] can now have their moves calculated depending on which piece they are and we will know they start on the square resulting from a as it's rank coordinate and b as it's file coordinate.

Knowing what file and rank numbers they start on can help us calculate what coordinates they can go to.

For now I will focus on the queen move generation.

By putting a switch statement inside the two for statements we can process each piece differently as they move differently.

Example:

	for (a = 0; a < 8; a++){
		for (b = 0; b < 8; b++){
			switch (board[a][b]) {
				case queen:
				
				/* calculate queen moves */
				
				break;
				case rook:
				
				/* calculate rook moves */
				
				break;
				case bishop:
				
				/* calculate bishop moves */
				
				break;
				case knight:
				
				/* calculate knight moves */
				
				break;
				case pawn:
				
				/* calculate pawn moves */
				
				break;
				case king:
				
				/* calculate king moves */
				
				break;
			}
		}
	}		



It is important to use break; after each case, without that break statement it would start generating moves for the last piece found as something it isn't.

For example, without the breaks, say it found a knight and generated all the knight moves, good! then it would run over to the next case, which would be pawn moves and start generating moves for the knight as if it were a pawn, and then as if it were a king!

Well no one wants that.

Although it is sometimes useful to not use a break because you want a sequence of things done for some things and not so much the last/later thing (case/switch), I just can't think of any!

				case queen:
					{
						for (e = -1; e <= 1; e++) {
						for (f = -1; f <= 1; f++) {
							c = a + e;
							d = b + f;
							if (!(f == 0 && e == 0)) { // process  the following code provided f and e are not both 0
								do {
									if (bounds(c, d)) {
										
										if (board[c][d] == 0) {
											fromSQa[z] = a;
											fromSQb[z] = b;
											toSQa[z] = c;
											toSQb[z] = d;
											z++;
										}
										if (board[c][d] < 0) {
											fromSQa[z] = a;
											fromSQb[z] = b;
											toSQa[z] = c;
											toSQb[z] = d;

											z++;
											break; 
										}
										if (board[c][d] > 0) break; 
										c = c + e;
										d = d + f;
									}
								}
								while (!(bounds(c, d) == false));
							
							}
							
						}
					}

				break;


Now above is the complicated part.

Now that the square for coordinate of a and b is found to have a white queen on it, we have to generate it's legal moves.

						for (e = -1; e <= 1; e++) {
						for (f = -1; f <= 1; f++) {


The above code will give us the directions a queen move, all cominations of -1, 0 and one for both e and f. Starting at -1, -1, and ending at +1, +1. For example, suppose our white queen is on h8 (7, 7), when we add -1, and -1 we get the coordinates for the g7 square (6, 6). as you can see we are moving diagonally down the board one square, and if we add it again we get f6 (5, 5), so repeatedly adding these values we keep going diagonally down the board, which is how a bishop or queen can move. Now for the next f and e values we have 0, -1, if we add these repeating as we did before we get the queen moving like a rook across the back rank, ie h8, to g8, to f8, to e8, to d8, to c8 and so on till it goes off the board. The only two values we don't need to add are 0, 0, because it would stay on it's square and not generate any moves. So we add some logic to leave out doing anything except getting the next direction in e and f. Below:

if (!(f == 0 && e == 0)) { // process  the following code provided f and e are not both 0


Now that we have excluded the direction 0, 0, all the remaining directions are either the way a bishop or a rook moves diagonally (4 directions), and up down left and right.

So here's the code that does that:

							c = a + e;
							d = b + f;
							if (!(f == 0 && e == 0)) { // process  the following code provided f and e are not both 0
do {
									if (bounds(c, d)) {
										
										if (board[c][d] == 0) {
											fromSQa[z] = a;
											fromSQb[z] = b;
											toSQa[z] = c;
											toSQb[z] = d;
											z++;
										}
										if (board[c][d] < 0) {
											fromSQa[z] = a;
											fromSQb[z] = b;
											toSQa[z] = c;
											toSQb[z] = d;

											z++;
											break; 
										}
										if (board[c][d] > 0) break; 
										c = c + e;
										d = d + f;
									}
								}
								while (!(bounds(c, d) == false));
							}



Now assuming the white queen is on h8, then a, b, are 7, 7, starting with c = a + e;,d = b + f;, well we know e and f both start at -1, so lets do the math c = a + e; well a is 7 e is -1 therefore c = 7 + (-1), so c == -6, and d = 7 + (-1), next if (!(f == 0 && e == 0)) { checks that f and e are not both == 0, since the condition returns true we continue inside the if statement here, inside the if statement we have a do-while loopdo { well nothing happens here because the while condition for this do-while loop is at the bottom in while (!(bounds(c, d) == false));, now say g7 square is unoccupied, well if (bounds(c, d)) {, well we know c == 6 and d == 6 so both of these on on the board (between 0 - 7, more than 7 is off the board or less than 0 is off the board also, so bounds returns true, and we continue inside this if statement also, now if board[c][d] (board[6][6]) is unoccupied, it will be equal to 0, so this statement if (board[c][d] == 0) { will return true and we continue inside this if statement too.

										if (board[c][d] == 0) {
											fromSQa[z] = a;
											fromSQb[z] = b;
											toSQa[z] = c;
											toSQb[z] = d;
											z++;
										}

So the above code saves the two from square coordinates and the two to square coordinates as integers, lets assume z ==0, our index for this move is zero, after saving the movce coordinates we increment z for the next move to be saved in our parallel arrays (same as above).

The next statement we encounter is if (board[c][d] < 0) {, since board[c][d] == 0 we can skip over what's inside this if statement, next up is if (board[c][d] > 0) break; , since this returns false also we can skip over break;.

Now,

										c = c + e;
										d = d + f;


we take c + e and get 6 + (-1) and put that into c, so c now equals 5. And the same with d except with d = d + f; d = 6 + (-1); d = 5, now we are at the end of the top if statement with the bounds() check in it }.

}while (!(bounds(c, d) == false));
since c and d are 5 and 5 the square is on the board so the statement in while(...) is true, and we continue at the top of the do-while loop, if (bounds(c, d)) { will return true, let's look at where that starts and ends:

if (bounds(c, d)) {
										
										if (board[c][d] == 0) {
											fromSQa[z] = a;
											fromSQb[z] = b;
											toSQa[z] = c;
											toSQb[z] = d;
											z++;
										}
										if (board[c][d] < 0) {
											fromSQa[z] = a;
											fromSQb[z] = b;
											toSQa[z] = c;
											toSQb[z] = d;

											z++;
											break; 
										}
										if (board[c][d] > 0) break; 
										c = c + e;
										d = d + f;
									}
								}



Now c and d are the coordinates for f6 on the chess board (or 5, 5), now assume that square contains a black piece, all black pieces have a value less than zero or a negative integer value. Well if (board[c][d] == 0) { will not return true, so we won't process till the next '}', now if (board[c][d] < 0) { will be tru inside the brackets so we continue with:

											fromSQa[z] = a;
											fromSQb[z] = b;
											toSQa[z] = c;
											toSQb[z] = d;

											z++;
											break; 



this saves the move coordinates in our 4 parallel arrays and increments the array index by 1. But instead this time we have a break statement after saving the move, the break takes us out of the do-while loop which takes us back to:

						for (f = -1; f <= 1; f++) {



Now f is incremented by 1, it was -1, now it's 0, and e is still -1.

							c = a + e;
							d = b + f;
							if (!(f == 0 && e == 0)) { // process  the following code provided f and e are not both 0
do {
									if (bounds(c, d)) {
										
										if (board[c][d] == 0) {
											fromSQa[z] = a;
											fromSQb[z] = b;
											toSQa[z] = c;
											toSQb[z] = d;
											z++;
										}
										if (board[c][d] < 0) {
											fromSQa[z] = a;
											fromSQb[z] = b;
											toSQa[z] = c;
											toSQb[z] = d;

											z++;
											break; 
										}
										if (board[c][d] > 0) break; 
										c = c + e;
										d = d + f;
									}
								}
								while (!(bounds(c, d) == false));
							}



Which brings us back to:

							c = a + e;
							d = b + f;



Now c is set to a + e, we know e equals -1 still and a = 7, so c = 7 + (-1), c = 6, and d = 7 + 0, so d = 7, now we are moving down like a rook, decrementing the rank but keeping on the same file, lets assume h7 contains a white piece, the next statement will be if (!(f == 0 && e == 0)) {, since e = -1, '(f == 0 && e == 0) will return false, so we have that break down to if (!false) {, and the opposite of false is tryue so we will continue inside the if statement open brace ('}').

The next statement is if (bounds(c, d)) {, since c and d are in the bounds of 0-7 we will continue inside this if statement as well. Next if (board[c][d] == 0) {, in this situation since c, d coordinates on the board contain a positive value piece we don't continue inside this if statement. Next if (board[c][d] < 0) { again won't be true either, so next is if (board[c][d] > 0) break; which will return true in the brackets of the if statement, since it's detected a friendly piece a move will not be saved nor will z be incremented (otherwise we'd be saving a move that captures a friendly piece), but we do go to break; which takes us back to the for statement for f to increment to 1, since we can't continue processing in that direction as we'd be generating queen moves in that direction through a friendly piece thus we terminate that direction with the break statement, and it continues on saving all moves that continue on empty squares saving them as moves until we hit a non empty square, or go off the board and capturing opposite polarity of pieces only.

If you follow so far you can work this out in your head from here.

That covers at least queen moves so far and the rook move generator and bishop moves are almost identical except for this line if (!(f == 0 && e == 0)) {.

The knight and king moves are much simpler as they are not repeating in the directions the move and attack.

That's all for now and thanks.
Was This Post Helpful? 0
  • +
  • -

  • (3 Pages)
  • +
  • 1
  • 2
  • 3