昨天弄了下午把第四次作业终于完整实现了。 不多说了,贴上完整的源代码 Hangman.java /* * File: Hangman.java * ------------------ * This program will eventually play the Hangman game from * Assignment #4. */ //import acm.graphics.*; import acm.program.*; import acm.util.*; //import java.awt.*; public class Hangman extends ConsoleProgram { private static final String strWelcome = "Welcome to Hangman!"; private static final String strTip = "The word now looks like this: "; public void run() { /* You fill this in */ gameInit(); //游戏初始化 gamePlay(); //进行游戏 } /* 界面框架初始化 */ public void init() { canvas = new HangmanCanvas(); add(canvas); } /* * ****************************************** * 函数名: gameInit * 功 能: 对游戏界面和相关变量进行 * 初始化 * ****************************************** */ private void gameInit() { /* 左边终端初始化 */ println(strWelcome); //输出欢迎信息 /* 初始化目标单词和用户所猜单词变量 */ originWord = lexicon.getWord(rgen.nextInt(0,lexicon.getWordCount()-1)); guessWord = "-"; for(int i= 1;i < originWord.length();i++){ guessWord += "-"; } //println(originWord);//输出所选单词 /* 右端窗口初始化 */ canvas.reset(); } /* * ****************************************** * 函数名: gameplay * 功 能: 游戏开始 * ****************************************** */ private void gamePlay() { boolean isLive = false;//判断是否在规定次数内成功 int leftTimes = 8;originWord.length(); //剩余次数 String strCh = null, //用户所猜字母 /* 猜测正确提示信息 */ guessRight = "That guess is correct"; while(!guessWord.equals(originWord)){ isLive = false; println(strTip + guessWord); //输出单词提示信息 println("You have " + leftTimes + " guesses left."); //输出剩余次数提示信息 strCh = readLine("Your guess: "); //读取用户所猜测的字母 while(strCh.length() > 1){ println("One character, one time."); strCh = readLine("Your guess: "); //读取用户所猜测的字母 } strCh = strCh.toUpperCase(); //将读取到的字母统一为大写 /* 判断是否猜测正确 */ for(int index=0;index < originWord.length();index++){ if(strCh.charAt(0) == originWord.charAt(index)){ if(0 == index){ guessWord = strCh + guessWord.substring(1); } else if(originWord.length() == (index +1)){ guessWord = guessWord.substring(0, index) + strCh; } else{ guessWord = guessWord.substring(0, index) + strCh + guessWord.substring(index+1); } isLive = true; } } canvas.displayWord(guessWord); //在右边窗口中显示单词的猜测情况 /* 输出相应信息 */ if(isLive){ //猜测正确 println(guessRight); } else{ //猜测错误 println("There are no " + strCh +"'s in the word."); leftTimes--; canvas.noteIncorrectGuess(strCh.charAt(0)); } if(0 == leftTimes) break; //剩余次数用完,退出 } if(isLive){ println("You guessed the word: " + originWord); println("You win."); } else{ println("You're completely hung."); println("The word was: " + originWord); println("You lose"); } } /* 私有实例变量 */ private String originWord; private String guessWord; private HangmanCanvas canvas; private HangmanLexicon lexicon = new HangmanLexicon(); private RandomGenerator rgen = RandomGenerator.getInstance(); } HangmanLexicon.java /* * File: HangmanLexicon.java * ------------------------- * This file contains a stub implementation of the HangmanLexicon * class that you will reimplement for Part III of the assignment. */ //import acm.util.*; import java.io.*; import java.util.*; public class HangmanLexicon { public HangmanLexicon(){ try { rd = new BufferedReader(new FileReader("HangmanLexicon.txt")); while(true){ String strTmp = rd.readLine(); if(strTmp == null) break; lexicon.add(strTmp); } rd.close(); } catch (IOException e) { System.out.println("Read file false!" + e); } } /** Returns the number of words in the lexicon. */ public int getWordCount() { // return 10; return lexicon.size(); } /** Returns the word at the specified index. */ public String getWord(int index) { // switch (index) { // case 0: return "BUOY"; // case 1: return "COMPUTER"; // case 2: return "CONNOISSEUR"; // case 3: return "DEHYDRATE"; // case 4: return "FUZZY"; // case 5: return "HUBBUB"; // case 6: return "KEYHOLE"; // case 7: return "QUAGMIRE"; // case 8: return "SLITHER"; // case 9: return "ZIRCON"; // default: throw new ErrorException("getWord: Illegal index"); // } return lexicon.get(index); } /* private instance variables */ private ArrayList<String> lexicon = new ArrayList<String>(); private BufferedReader rd; } HangmanCanvas.java /* * File: HangmanCanvas.java * ------------------------ * This file keeps track of the Hangman display. */ import acm.graphics.*; public class HangmanCanvas extends GCanvas { /** Resets the display so that only the scaffold appears */ public void reset() { /* You fill this in */ removeAll(); // 移除窗口中的所有对象 /* 绘制绞架 */ //Scaffold drawLine(getWidth() / 2 - BEAM_LENGTH, (getHeight() - SCAFFOLD_HEIGHT) / 2, getWidth() / 2 - BEAM_LENGTH, (getHeight() + SCAFFOLD_HEIGHT) / 2); //Beam drawLine(getWidth()/2 - BEAM_LENGTH, (getHeight() - SCAFFOLD_HEIGHT)/2, getWidth()/2, (getHeight() - SCAFFOLD_HEIGHT)/2); /* 两个标签 */ add(wordInfo,40,(getHeight()+SCAFFOLD_HEIGHT)/2 + 10); //单词猜测情况 add(wrongList,40,(getHeight()+SCAFFOLD_HEIGHT)/2 + 40); //猜测错误的字母 } /** * Updates the word on the screen to correspond to the current state of the * game. The argument string shows what letters have been guessed so far; * unguessed letters are indicated by hyphens. */ public void displayWord(String word) { /* You fill this in */ wordInfo.setFont("Serif-20"); wordInfo.setLabel(word); } /** * Updates the display to correspond to an incorrect guess by the user. * Calling this method causes the next body part to appear on the scaffold * and adds the letter to the list of incorrect guesses that appears at the * bottom of the window. */ public void noteIncorrectGuess(char letter) { /* You fill this in */ String guessWord; wrongList.setLabel(wrongList.getLabel() + String.valueOf(letter)); guessWord = wrongList.getLabel(); switch(guessWord.length()){ case 1: //Rope drawLine(getWidth()/2, (getHeight() - SCAFFOLD_HEIGHT)/2, getWidth()/2, (getHeight() - SCAFFOLD_HEIGHT)/2 + ROPE_LENGTH); break; case 2: //Head GOval head = new GOval((getWidth()/2 - HEAD_RADIUS), (getHeight() - SCAFFOLD_HEIGHT)/2 + ROPE_LENGTH, 2 * HEAD_RADIUS,2 * HEAD_RADIUS); add(head); head.move(0, -40); break; case 3: //Body drawLine(getWidth()/2, (getHeight() - SCAFFOLD_HEIGHT)/2 + ROPE_LENGTH + 2 * HEAD_RADIUS, getWidth()/2, (getHeight() - SCAFFOLD_HEIGHT)/2 + ROPE_LENGTH + 2 * HEAD_RADIUS + BODY_LENGTH); break; case 4: //Left Arm //Upper Arm drawLine(getWidth()/2 - UPPER_ARM_LENGTH, (getHeight() - SCAFFOLD_HEIGHT)/2 + ROPE_LENGTH + 2 * HEAD_RADIUS + ARM_OFFSET_FROM_HEAD, getWidth()/2, (getHeight() - SCAFFOLD_HEIGHT)/2 + ROPE_LENGTH + 2 * HEAD_RADIUS + ARM_OFFSET_FROM_HEAD); //Lower Arm drawLine(getWidth()/2 - UPPER_ARM_LENGTH, (getHeight() - SCAFFOLD_HEIGHT)/2 + ROPE_LENGTH + 2 * HEAD_RADIUS + ARM_OFFSET_FROM_HEAD, getWidth()/2 - UPPER_ARM_LENGTH, (getHeight() - SCAFFOLD_HEIGHT)/2 + ROPE_LENGTH + 2 * HEAD_RADIUS + ARM_OFFSET_FROM_HEAD + LOWER_ARM_LENGTH); break; case 5: //Right Arm //Upper Arm drawLine(getWidth()/2, (getHeight() - SCAFFOLD_HEIGHT)/2 + ROPE_LENGTH + 2 * HEAD_RADIUS + ARM_OFFSET_FROM_HEAD, getWidth()/2 + UPPER_ARM_LENGTH, (getHeight() - SCAFFOLD_HEIGHT)/2 + ROPE_LENGTH + 2 * HEAD_RADIUS + ARM_OFFSET_FROM_HEAD); //Lower Arm drawLine(getWidth()/2 + UPPER_ARM_LENGTH, (getHeight() - SCAFFOLD_HEIGHT)/2 + ROPE_LENGTH + 2 * HEAD_RADIUS + ARM_OFFSET_FROM_HEAD, getWidth()/2 + UPPER_ARM_LENGTH, (getHeight() - SCAFFOLD_HEIGHT)/2 + ROPE_LENGTH + 2 * HEAD_RADIUS + ARM_OFFSET_FROM_HEAD + LOWER_ARM_LENGTH); break; case 6: //Hip drawLine((getWidth() - HIP_WIDTH)/2, (getHeight() - SCAFFOLD_HEIGHT)/2 + ROPE_LENGTH + 2 * HEAD_RADIUS + BODY_LENGTH, (getWidth() + HIP_WIDTH)/2, (getHeight() - SCAFFOLD_HEIGHT)/2 + ROPE_LENGTH + 2 * HEAD_RADIUS + BODY_LENGTH); break; case 7: //Left Leg drawLine((getWidth() - HIP_WIDTH)/2, (getHeight() - SCAFFOLD_HEIGHT)/2 + ROPE_LENGTH + 2 * HEAD_RADIUS + BODY_LENGTH, (getWidth() - HIP_WIDTH)/2, (getHeight() - SCAFFOLD_HEIGHT)/2 + ROPE_LENGTH + 2 * HEAD_RADIUS + BODY_LENGTH + LEG_LENGTH); //Left Foot drawLine((getWidth() - HIP_WIDTH)/2, (getHeight() - SCAFFOLD_HEIGHT)/2 + ROPE_LENGTH + 2 * HEAD_RADIUS + BODY_LENGTH + LEG_LENGTH, (getWidth() - HIP_WIDTH)/2 - FOOT_LENGTH, (getHeight() - SCAFFOLD_HEIGHT)/2 + ROPE_LENGTH + 2 * HEAD_RADIUS + BODY_LENGTH + LEG_LENGTH); break; case 8: //Right Leg drawLine((getWidth() + HIP_WIDTH)/2, (getHeight() - SCAFFOLD_HEIGHT)/2 + ROPE_LENGTH + 2 * HEAD_RADIUS + BODY_LENGTH, (getWidth() + HIP_WIDTH)/2, (getHeight() - SCAFFOLD_HEIGHT)/2 + ROPE_LENGTH + 2 * HEAD_RADIUS + BODY_LENGTH + LEG_LENGTH); //Right Foot drawLine((getWidth() + HIP_WIDTH)/2, (getHeight() - SCAFFOLD_HEIGHT)/2 + ROPE_LENGTH + 2 * HEAD_RADIUS + BODY_LENGTH + LEG_LENGTH, (getWidth() + HIP_WIDTH)/2 + FOOT_LENGTH, (getHeight() - SCAFFOLD_HEIGHT)/2 + ROPE_LENGTH + 2 * HEAD_RADIUS + BODY_LENGTH + LEG_LENGTH); } } /* * ****************************************** * 函数名: drawLine * 功 能: 绘制线段 * 参 数: startX —— 起始点X坐标 * startY —— 起始点Y坐标 * endX —— 终点X坐标 * endY —— 终点Y坐标 * ****************************************** */ private void drawLine(double startX, double startY, double endX, double endY) { GLine line = new GLine(startX,startY,endX,endY); add(line); line.move(0, -40); } /* Constants for the simple version of the picture (in pixels) */ private static final int SCAFFOLD_HEIGHT = 360; private static final int BEAM_LENGTH = 144; private static final int ROPE_LENGTH = 18; private static final int HEAD_RADIUS = 36; private static final int BODY_LENGTH = 144; private static final int ARM_OFFSET_FROM_HEAD = 28; private static final int UPPER_ARM_LENGTH = 72; private static final int LOWER_ARM_LENGTH = 44; private static final int HIP_WIDTH = 36; private static final int LEG_LENGTH = 108; private static final int FOOT_LENGTH = 28; /* 私有实例变量 */ private GLabel wrongList = new GLabel(""); private GLabel wordInfo = new GLabel(""); } 最后附上几张实际的图片: