Code:
#include "primlib.h"
#include <stdlib.h>
#include <stdio.h>
#include <math.h>
/** number of pegs*/
#define n 3
/**number of disks*/
#define d 3
int towers[n][d]; /*initialization of the array (pegs x disks) */
int x,i,j,choice,disknum,mem,A,B;
/*declaration of variables
x - piece of the screen, dependent on the peg number, used to place the pegs in the equidistant way
i,i - loop variables
choice - typed peg (shifted by 1, in the function shift_key, so that the index starts from 0)
disknum - number of disks on the peg
mem - auxiliary variable, used to store the disks during the operation of moving between pegs
A, B - replacements of choice and disknum-1, to simplify further uses of the array
*/
void pegdraw(void) /**function drawing the pegs*/
{
int i=1;
while (i<=n)
{
filledRect(i*((screenWidth())/(n+1))-15/n, screenHeight()-(20*d+20),i*((screenWidth()/(n+1)))+15/n, screenHeight()-21, RED);
updateScreen();
i++;
}
}
void diskdraw(void) /**function drawing the disks*/
{
x=screenWidth()/(n+1);
for (i=0;i<n;i++)
{
for(j=0;j<d;j++)
{
if (towers[i][j]==0)
{}
else
{
filledRect((i+1)*x-(30*towers[i][j])/(n+1),screenHeight()-37-20*j,(i+1)*x+(30*towers[i][j])/(n+1), screenHeight()-21-20*j,GREEN);
}
}
}
}
void shift_key(void) /**function assigning the typed key to the actual posision in the array*/
{
if (isKeyDown(SDLK_1)) choice=0;
if (isKeyDown(SDLK_2)) choice=1;
if (isKeyDown(SDLK_3)) choice=2;
if (isKeyDown(SDLK_4)) choice=3;
if (isKeyDown(SDLK_5)) choice=4;
if (isKeyDown(SDLK_6)) choice=5;
if (isKeyDown(SDLK_7)) choice=6;
if (isKeyDown(SDLK_8)) choice=7;
if (isKeyDown(SDLK_9)) choice=8;
if (isKeyDown(SDLK_0)) choice=9;
}
int disk_amount(int choice) /**function reading the number of disks, which are present on the peg*/
{
disknum=0;
for (i=0;i<d;i++)
{
if(towers[choice][i]==0)
{
break;
}
else
{
disknum=disknum+1;
}
}
return disknum;
}
int main(int argc, char* argv[])
{
int i,j;
if (initGraph())
exit(3);
filledRect(0,screenHeight()-20,screenWidth()-1,screenHeight()-1, YELLOW);/* drawing the ground for the pegs*/
textout((screenWidth()/2)-40,50,"Instructions",WHITE); /*instructions*/
textout(30,70,"The objective is to move all the disks from the initial stack to the other",WHITE);
textout(30,90,"one.You can only move a disk on an empty peg, or on a bigger disk (not on a",WHITE);
textout(30,110,"smaller).To move, type the number of the source peg (from the left), and",WHITE);
textout(30,130,"then the number of the destination peg.",WHITE);
for (i=0;i<n;i++)
{
for(j=0;j<d;j++)
{
if(i==0)
{
towers[i][j]=d-j;
}
else towers [i][j]=0;
}
}
pegdraw();
diskdraw();
do
{
if(isKeyDown(SDLK_ESCAPE))
{
break; /*optional closing the program*/
}
fflush(stdin);
getkey(); /*choice of source peg*/
shift_key(); /*assigning the typed key to the actual posision in the array*/
disk_amount(choice);
mem=towers[choice][disknum-1]; /*auxiliary variable 'mem', used to store the user's peg choice and number of disks*/
A=choice;
B=disknum-1;
/*protection from typing keys too fast (otherwise the program could store two keys together */
getkey(); /*choice of destination peg*/
shift_key(); /*assigning the typed key to the actual posision in the array*/
disk_amount(choice);
if(A==choice)
{
continue; /*if both pegs choosen are the same, nothing happens*/
}
if(choice>n-1)
{
continue; /*if a chosen peg has a greater number, than the total amount of pegs, nothing happens. subtraction of 1 indicates, that the peg table index is shifted by 1*/
}
if(towers[choice][0]!=0 && mem>towers[choice][disknum-1])
{
continue; /*if the chosen disk is bigger, than the disk on the top of the destination peg, nothing happens*/
}
towers[A][B]=0; /*clearing the variable, so that next execution can be performed from the beginning*/
towers[choice][disknum]=mem; /*moving the disk to the destination peg, above the last disk on it*/
updateScreen();
if(towers[n-1][d-1]>0)
{
textout(screenWidth()/2, 50, "YOU WIN", BLUE);
break; /*all disks are on the last peg - program terminates*/
}
}while(1);
updateScreen();
getkey();
return 0;
}