/*
"Schiffe" versenken
(Wären das dann nicht eigendlich U-Boote wenn man sie nur sieht wenn sie getroffen wurden?)
Code geschrieben von Tobias Schmidt
Legende:
~ - Wasser
S - Schiff
o - Getroffenes "Schiff"
x - Fehlgeschlagener Schuss
Developer Log:
19.10.2017 - 10:00 - Irgendwie geht da was nicht.
19.10.2017 - 11:47 - Fast den kleinen Schrank zerlegt.
19.10.2017 - 11:49 - Der mist funktioniert nicht ...
20.10.2017 - 8:00 - Es geht endlich! \(0.0)/
*/
#include <stdio.h>
#include <stdbool.h>
#include <time.h>
#include <stdlib.h>
#include <unistd.h>
#define sizeX 8
#define sizeY 8
#define sizeTotal ((sizeX+1)*10+sizeY)
#define maxCachedGegnerZuege 4
#define maxShips sizeX+sizeX
// Interne Variablen
#define wasser 0
#define daneben 1
#define treffer 2
#define schiff 3
#define bereits_Daneben 11
#define bereits_Getroffen 22
#define player1_Gewonnen 42 // Lösung auf alles.
#define player1_Verloren 31 // 31 hör zu, eine Line macht dich nicht cool ...
// Das sieht man später anstatt der Variablen
#define wasser_Icon "~ "
#define daneben_Icon "x "
#define treffer_Icon "� "
#define schiff_Icon "0 "
static int spielFeldPlayer[sizeTotal] = { 0 }; // static soll sicherstellen das auch
static int spielFeldGegner[sizeTotal] = { 0 }; // wirklich nur DIESE variable genutzt wird, und keine kopie
static int playerShipsLeft;
static int gegnerShipsLeft;
static int mode;
static bool spieler1AmZug = true;
static bool spielVerlassen = false;
static bool zumHauptmenu = false;
static int letzteComputerZuege[maxCachedGegnerZuege][2];
static int computerZuege = 0;
static int rundenZaehler;
static int timeSinceStart;
// Headerkrams
void generiereSpielFeld(bool istSpieler1);
void zeigeSpielFeld(bool nurGetroffen);
int macheSpielZug (int zugX, int zugY);
bool menschlicherSpielZug(int debugx, int debugy);
bool computerSpielZug(bool rekursive);
void clear();
void showFieldHeader();
void showFieldHeader() {
int sekunde = (int)(time(NULL)-timeSinceStart), minute = 0;
while(sekunde > 60)
{
sekunde -= 60;
minute++;
}
printf("Runde %d | Zeit: %.2d:%.2d\n", rundenZaehler, minute, sekunde);
if (spieler1AmZug && mode == 1) printf("\n\t\tDu bist am Zug!\n"
"\tKI Schiffe: %d | Deine Schiffe: %d\n", gegnerShipsLeft, playerShipsLeft);
else if (spieler1AmZug && mode == 2) printf("\n\t\tSpieler 1 ist am Zug!\n"
"\tSchiffe Spieler 2: %d | Deine Schiffe: %d\n", gegnerShipsLeft, playerShipsLeft);
else if (!spieler1AmZug && mode == 2) printf("\n\t\tSpieler 2 ist am Zug!\n"
"\tSchiffe Spieler 1: %d | Deine Schiffe: %d\n", playerShipsLeft, gegnerShipsLeft);
else if (spieler1AmZug && mode == 3) printf("\n\t\tTestmodus\n");
else if (!spieler1AmZug && mode == 1) printf("\n\t\tDie KI ist am Zug!\n"
"\tKI Schiffe: %d | Deine Schiffe: %d\n", gegnerShipsLeft, playerShipsLeft);
}
void clear() {
printf("\e[1;1H\e[2J");
}
bool computerSpielZug(bool rekursive) {
bool ret = false;
if (!rekursive) {
clear();
showFieldHeader();
zeigeSpielFeld(false);
sleep(1);
}
int nextx = rand() % sizeX-1;
int nexty = rand() % sizeY-1;;
/*if(computerZuege == 0){ // Es geht, ich fasse hier nichtsmehr an!
nextx = rand() % sizeX-1;
nexty = rand() % sizeY-1;
letzteComputerZuege[computerZuege][0] = nextx;
letzteComputerZuege[computerZuege][1] = nexty;
computerZuege++;
} */
int status = macheSpielZug(nextx, nexty);
//if (!rekursive) {
clear();
showFieldHeader();
zeigeSpielFeld(false);
//}
if (status == treffer) {
printf("\n\t Verdammt! Der Computer hat eins unserer Schiffe versenkt\n");
} else if (status == daneben) {
//ret = computerSpielZug(true);
printf("\n\t Daneben! - Uns kann nichts aufhalten!\n");
} else if (status == bereits_Daneben) {
ret = computerSpielZug(true);
//printf("\n\t Erneut Daneben... - Das sollte eigendlich nicht möglich sein ...!\n");
} else if (status == player1_Gewonnen) {
printf("\n\t SIEG! Wir haben gewonnen!!\n");
ret = true;
} else if (status == player1_Verloren) {
printf("\n\t NIEDERLAGE! Der Computer hat gewonnen..\n");
ret = true;
}
else if ( status == bereits_Getroffen) {
ret = computerSpielZug(true);
//printf("\n\t Schiff bereits getroffen! - Entwickler hat verpennt das zu vermeiden...\n");
}
else {
printf("\n\t Unbekannter Zustand... Der Entwickler ist immernoch Doof!\n");
}
if (!rekursive){
sleep(3);
clear();
}
return ret;
}
bool menschlicherSpielZug(int debugx, int debugy) {
showFieldHeader();
if (mode == 3) zeigeSpielFeld(false);
else zeigeSpielFeld(true);
int nextx;
if (debugx == -1){
do { // Nested Loop, hurray!
printf("\n\t Naechster Zug: X Koordinate: ");
scanf("%d", &nextx);
nextx--;
if (nextx > sizeX-1)
{
printf("\tDie X Koordinate ist zu gross!\n");
} else if (nextx < 0) {
printf("\tDie X Koordinate ist zu klein!\n");
} else {
break;
}
} while (1);
} else nextx = debugx;
int nexty;
if (debugy == -1) {
do { // Nested Loop again, hurray!
printf("\n\t Naechster Zug: Y Koordinate: ");
scanf("%d", &nexty);
nexty--;
if (nexty > sizeY-1)
{
printf("\tDie Y Koordinate ist zu gross!");
} else if (nexty < 0) {
printf("\tDie Y Koordinate ist zu klein!");
} else {
break;
}
} while (1);
} else nexty = debugy;
if (mode == 3 || mode == 4) printf("X: %d - Y: %d", nextx, nexty);
int status = macheSpielZug(nextx, nexty);
clear();
showFieldHeader();
if (mode == 3) zeigeSpielFeld(false);
else zeigeSpielFeld(true);
if (status == treffer) {
printf("\n\t TREFFER! - Gegnerisches Schiff versenkt!\n");
} else if (status == daneben) {
printf("\n\t Daneben! - Leider nur Wasseratome getroffen!\n");
} else if (status == bereits_Daneben) {
printf("\n\t Immernoch Daneben! - Hier ist nach wie vor kein Schiff!\n\t\t\tNeuer versuch!\n");
sleep(2);
clear();
return menschlicherSpielZug(debugx, debugy);
} else if (status == player1_Gewonnen) {
printf("\n\t SIEG! Spieler 1 Hat gewonnen!!\n");
return true;
} else if (status == player1_Verloren) {
if(mode == 1) printf("\n\t NIEDERLAGE! Der Computer hat gewonnen..\n");
else printf("\n\t SIEG! Spieler 2 Hat gewonnen!!\n");
return true;
}
else if ( status == bereits_Getroffen) {
printf("\n\t Schiff bereits getroffen! - Die sind doch bereits alle tot!...\n\t\t\tNeuer Versuch!");
sleep(2);
clear();
return menschlicherSpielZug(debugx, debugy);
}
else {
printf("\n\t Unbekannter Zustand... Der Entwickler ist Doof!\n");
}
sleep(2);
clear();
return false;
}
int macheSpielZug (int zugX, int zugY) {
int status = -1;
if (spieler1AmZug) status = spielFeldGegner[(zugX*10)+zugY];
else status = spielFeldPlayer[(zugX*10)+zugY];
if (status == schiff) {
if (spieler1AmZug) {
spielFeldGegner[(zugX*10)+zugY] = treffer;
gegnerShipsLeft--;
if(gegnerShipsLeft == 0) return player1_Gewonnen;
}
else {
spielFeldPlayer[(zugX*10)+zugY] = treffer;
playerShipsLeft--;
if(playerShipsLeft == 0) return player1_Verloren;
}
return treffer;
}
else if (status == daneben) return bereits_Daneben;
else if (status == wasser) {
if (spieler1AmZug) spielFeldGegner[(zugX*10)+zugY] = daneben;
else spielFeldPlayer[(zugX*10)+zugY] = daneben;
return daneben;
}
else if (status == treffer) return bereits_Getroffen;
}
void generiereSpielFeld(bool istSpieler1) {
int totalShipps = 0;
/*for (int x = 0; x < sizeX; x++)
{
for (int y = 0; y < sizeY; y++)
{
if(istSpieler1) spielFeldPlayer[x][y] = 0;
else spielFeldGegner[x][y] = 0;
}
}*/
for (int k = 0; k<maxShips; k++) {
int x = rand() % sizeX;
int y = rand() % sizeY;
if(istSpieler1)
{
if (spielFeldPlayer[(x*10)+y] != schiff) {
spielFeldPlayer[(x*10)+y] = schiff;
playerShipsLeft++;
}
else k--;
} else {
if (spielFeldGegner[(x*10)+y] != schiff) {
spielFeldGegner[(x*10)+y] = schiff;
gegnerShipsLeft++;
}
else k--;
}
}
}
void zeigeSpielFeld(bool nurGetroffen)
{
for (int y = 0; y < sizeY; y++)
{
for (int x = 0; x < sizeX; x++)
{
// AußenBorder Start
if (x == 0 && y == 0){
printf("\n\t\t# X ");
for (int k = 0; k < sizeX; k++)
{
printf("%d ", k+1);
}
printf("\n\t\tY\n\t\t1 ");
}
if (x == 0 && y != 0)
{
printf("\t\t%d ", y + 1);
}
// AußenBorder Ende
// Spielfeld Zeichnen Start
int toPrint = -1;
if(spieler1AmZug) toPrint = spielFeldGegner[(x*10)+y];
else toPrint = spielFeldPlayer[(x*10)+y];
if (nurGetroffen){
if(toPrint == schiff) toPrint = wasser;
}
switch (toPrint)
{
case wasser: printf(wasser_Icon); break;
case daneben: printf(daneben_Icon); break;
case treffer: printf(treffer_Icon); break;
case schiff: printf(schiff_Icon); break;
}
// Spielfeld Zeichnen Ende
}
//int temp;
//scanf("%d", &temp);
printf("\n");
}
}
int main() {
// Variablen Initialisieren
// Modi: 0 - Ungenutzt, 1 - gegen KI, 2 - 2 Spieler, 3 - Testmodus, 4 - Ein Feld automatisch ausfüllen.
bool spielVerlassen = false;
int debugx = 0;
int debugy = 0;
srand(time(NULL)); // Wir setzten einen Seed für den Zufallsgenerator.
clear();
printf("**********************************\n");
printf("* \"Schiffe\" versenken! Oder so...*\n");
printf("**********************************\n\n");
printf("\t\t Hauptmenue:\n");
printf("\t1) Neues Spiel (gegen KI)\n");
printf("\t2) Neues Spiel (2 Spieler Modus)\n");
printf("\t3) Testmodus\n");
printf("\t4) Autofill\n");
printf("\n\t0) Spiel Beenden\n");
printf("\n\tAuswaehlen: ");
int hauptMenue = 1;
scanf("%d", &hauptMenue);
switch (hauptMenue)
{
case 1: mode = 1; break;
case 2: mode = 2; break;
case 3: mode = 3; break;
case 4: mode = 4; break;
case 0: return 0; break; // break ist echt voll super sinnvoll hier. Echt jetzt... nicht ...
}
timeSinceStart = (int)time(NULL);
clear();
//generiereSpielFeld(false);
if(mode != 3 && mode != 4){
//printf("Generiere Spielfelder:");
//printf("\n\t- Spieler 1 Komplett -");
generiereSpielFeld(true); // Wir generieren für den Spieler das Spielfeld
//if (mode == 1) printf("\n\t- KI-Gegner Komplett - \n");
//else printf("\n\t- Spieler 2 Komplett - \n");
generiereSpielFeld(false); // Wir generieren für den (KI-)Gegner das Spielfeld
} else if (mode == 4) generiereSpielFeld(false);
else printf("\n");
do {
if (spieler1AmZug)
{
rundenZaehler++;
if (mode == 4) {
menschlicherSpielZug(debugx, debugy);
if (debugx < 7) debugx++;
else {
debugx = 0;
debugy++;
}
if (debugy == 8) {
spielVerlassen = !spielVerlassen;
break;
}
//sleep(1);
} else {
spielVerlassen = menschlicherSpielZug(-1, -1);
if (mode != 3) spieler1AmZug = !spieler1AmZug;
}
} else {
if (mode == 1) {
spielVerlassen = computerSpielZug(false);
spieler1AmZug = !spieler1AmZug;
} else {
spielVerlassen = menschlicherSpielZug(-1, -1); // Mode ist total sinnlos hier... | Wir das das Spielfeld von Spieler 1.
spieler1AmZug = !spieler1AmZug;
}
}
} while(!spielVerlassen);
return 0;
}
Comments
0 B
|👍
/👎