Marc Bax / Mbed 2 deprecated Flexbook180111a

Dependencies:   SDFileSystem app epson mbed msp430 pl tests

Revision:
0:c643d398cdb6
Child:
1:5874c1a074a7
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hangman.cpp	Thu Jan 11 13:42:27 2018 +0000
@@ -0,0 +1,275 @@
+
+
+#include "log.h"
+#include "hangman.h"
+#include "eink.h"
+#include "mbed.h"
+#include "SDFileSystem.h"
+
+namespace Flexbook
+{
+
+HangmanGame::HangmanGame()
+: finished(false), currentpos(13), oldpos(13),
+  alphabet(), word(""), guessed(""),
+  wordlength(0), hangstage(0)
+{
+    Log("Creating hangman game");
+    
+    // Display the game welcome screen
+     WriteImage("/base.pgm");
+    DrawMan(0);
+    UpdateDisplay();
+    
+    // Fill the array to indicate none of the letters has been used
+    for (int i=0; i<27; i++)
+    {
+        alphabet[i]=false;
+        }
+        
+    // Pick a random word from the hangdict.txt file, update *word, and return the number of characters
+    wordlength = ReturnWord(*word);
+    
+    //Change the word string so that "A" is 0, "M"=12, "N"=14 and "Z"=26
+    for (int i=0; i<wordlength; i++)
+    {
+        word[i] = word[i] - 65;
+        if (word[i] > 12) word[i] = word[i] + 1;
+        guessed[i]=13;
+        printf(" %u", word[i]);
+        }
+        
+    // Display the game start screen
+    printf("\n");
+    DrawWord(guessed, wordlength);
+    
+}
+
+HangmanGame::~HangmanGame()
+{
+    Log("deleting hangmangame");
+}
+
+// Function returning x-position of "letterpos" on the alphabet matrix
+int HangmanGame::Xpos(const char letterpos)
+{
+    int result;
+    result = 155 + ((letterpos%9)*25);
+    printf("xpos = %u, ", result);
+    return(result);
+}
+
+// Function returning y-position of "letterpos" on the alphabet matrix
+int HangmanGame::Ypos(const char letterpos)
+{
+    int result;
+    result = 21 + ((letterpos/9)*30);
+    printf("ypos = %u\n", result);
+    return(result);
+}
+
+// routine that redraws the alphabet matrix after a cursor move
+void HangmanGame::RedrawAlphabet(const char newpos, const char oldpos, const bool alphabet[27])
+{  
+    Log("redrawing newpos");
+    if (alphabet[newpos])
+        {
+        //writeimage of newpos letter greyed inverted
+        printf("writing %u grey inverted\n", newpos);
+        WritePartImage("/agi.pgm", Xpos(newpos), Ypos(newpos), newpos*25, 0, 24, 28);
+        }
+        else
+            {
+            //writeimage of newpos letter inverted
+            printf("writing %u inverted\n", newpos);
+            WritePartImage("/ai.pgm", Xpos(newpos), Ypos(newpos), newpos*25, 0, 24, 28);
+            }
+    Log("redrawing oldpos");
+    if (alphabet[oldpos])
+        {
+        //writeimage of oldpos letter greyed out
+        printf("writing %u greyed\n", oldpos);
+        WritePartImage("/ag.pgm", Xpos(oldpos), Ypos(oldpos), oldpos*25, 0, 24, 28);
+        }
+        else
+            {
+            //writeimage of oldpos letter normal
+            printf("writing %u normal\n", oldpos);
+            WritePartImage("/an.pgm", Xpos(oldpos), Ypos(oldpos), oldpos*25, 0, 24, 28);
+            }
+    // redraw the alphabet matrix based on a cursor move
+    UpdateDisplay();
+}
+
+//function to count number of eligible words in the dictionary file
+int HangmanGame::NumDictWords()
+{
+    FILE *fp1 = fopen("/sd/hangman/hangdict.txt", "r");
+    if (fp1 == NULL) {
+        printf("Could not open hangdict.txt\n");
+        }
+        else {
+            printf("hangdict.txt opened\n");
+            }
+    int wordcount = 0;
+    int wordlength = 0;
+    int ch;
+    while (EOF != (ch = getc(fp1))) {
+        // check if character is an LF. If the word on that line is the right length, increment word counter
+        if (ch == 10) {
+            if ((wordlength > 7) && (wordlength < 15)) {
+                wordcount = wordcount + 1;
+                }
+                wordlength = 0;
+            }
+        else {
+            // if the character is not an LF, increment character count
+            wordlength = wordlength + 1;
+            }
+        }
+    fclose(fp1);
+    printf("Word count: %u\n", wordcount);
+    return wordcount;
+}
+
+// routine to draw the current guess of the word on the display
+void HangmanGame::DrawWord(const char guessed[14], const char wordlength)
+{
+    for (int i = 0; i < wordlength; i++) {
+        WritePartImage("/an.pgm", 380-(25*(wordlength-i)), 191, guessed[i]*25, 0, 24, 28);
+        }
+    UpdateDisplay();
+}
+
+// routine to redraw the hanging man
+void HangmanGame::DrawMan(const char manstate)
+{
+    switch (manstate)
+    {       
+        case 0:
+            WritePartImage("/man0.pgm", 35, 0, 0, 0, 74, 174);
+            break;
+            
+        case 1:
+            WritePartImage("/man1.pgm", 35, 0, 0, 0, 74, 174);
+            break;
+            
+        case 2:
+            WritePartImage("/man2.pgm", 35, 0, 0, 0, 74, 174);
+            break;
+            
+        case 3:
+            WritePartImage("/man3.pgm", 35, 0, 0, 0, 74, 174);
+            break;
+            
+        case 4:
+            WritePartImage("/man4.pgm", 35, 0, 0, 0, 74, 174);
+            break;
+            
+        case 5:
+            WritePartImage("/man5.pgm", 35, 0, 0, 0, 74, 174);
+            break;
+            
+        case 6:
+            WritePartImage("/man6.pgm", 35, 0, 0, 0, 74, 174);
+            break;
+    }
+}                                                          
+
+// routine that picks a new word to guess, and returns the number of characters in the word
+char HangmanGame::ReturnWord(char &word2guess)
+{
+    //pick a random word from the hangdict.txt file
+    int wordindex = rand()%HangmanGame::NumDictWords();
+    FILE *fp1 = fopen("/sd/hangman/hangdict.txt", "r");
+    printf("Returning word: %u\n", wordindex);
+    for (int i = 0; i < wordindex; i++) {
+        fgets(&word2guess, 24, fp1);
+        while ((strlen(&word2guess) < 10) || (strlen(&word2guess) > 16)) {
+            fgets(&word2guess, 24, fp1);
+        }
+    }
+    printf("%s - length %u characters\n", &word2guess, strlen(&word2guess)-2);
+    fclose(fp1);
+    return (strlen(&word2guess)-2);
+}
+
+// routine to move the cursor on the alphabet matrix when a nav button is pressed
+// navbuttons: up=10; right=6; down=7; left=9; (select=8; cancel=5;)
+char HangmanGame::MoveCursor(const bool alphabet[27], const char buttonnumber, char oldpos)
+{
+    char newpos;
+    printf("%u, ", oldpos);
+    switch (buttonnumber)
+    {
+        case 10:
+            if (oldpos > 8)
+                newpos = oldpos-9;
+                else newpos=oldpos;
+                break;    
+            
+        case 7:
+            if (oldpos < 18)
+                newpos = oldpos+9;
+                else newpos=oldpos;
+                break;
+            
+        case 9:
+            if ((oldpos == 0) || (oldpos == 9) || (oldpos == 18))
+                newpos=oldpos;
+                else newpos=oldpos-1;
+                break;
+                
+        case 6:
+            if ((oldpos == 8) || (oldpos == 17) || (oldpos == 26))
+                newpos=oldpos;
+                else newpos=oldpos+1;
+                break;
+                
+        default:
+            newpos=13;
+        }
+    printf("%u\n", newpos);
+    if (newpos != oldpos) RedrawAlphabet(newpos, oldpos, alphabet);
+    Log("alphabet redrawn");
+    oldpos = newpos;
+    return(newpos);
+}
+
+// routine called when a letter is selected - unfinished work in progress
+bool HangmanGame::SelectLetter(const char letterpos, const char word2guess[14], const char wordlength, char* guessed[14], char hangmanstate)
+{
+    bool goodguess = false;
+    // If the word contains the selected letter, update the guess
+    for (int i=0; i < wordlength; i++)
+    {
+        if (word2guess[i]==letterpos)
+        {
+            *guessed[i]=letterpos;
+            goodguess = true;
+            }
+        }
+    // If guess is correct, update the displayed word
+    if (goodguess)
+    {
+        DrawWord(*guessed, wordlength);
+    }
+    
+    // If the guess was wrong, hang the next segment of the man
+    if (!goodguess)
+    {
+        hangmanstate = hangmanstate+1;
+        DrawMan(hangmanstate);
+    }
+        
+    //body
+    UpdateDisplay();
+    // The return value is false if the game is not finished yet, and true if the word is guessed or the man is hung
+    if ((hangmanstate==6) || (word2guess==*guessed))
+    {
+        return(true);
+        }
+        else return (false);
+}
+
+}