KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > hangman > Visit


1 /*******************************************************************************
2  * Copyright (c) 2004, Dirk von der Weiden.
3  * All rights reserved. This program and the accompanying materials
4  * are made available under the terms of the Common Public License v1.0
5  * which accompanies this distribution, and is available at
6  * http://www.eclipse.org/legal/cpl-v10.html
7  *
8  * Contributors:
9  * Dirk von der Weiden - initial API and implementation
10  *
11  * Created on 14.06.2004
12  *
13  * date: 23.06.2004
14  * project: WiSer-HangMan
15  *
16  * *******************************************************************************/

17
18 package hangman;
19
20 import java.util.*;
21
22 import Jmc.baseTools.*;
23 import Jmc.baseGui.*;
24 import Jmc.commonGui.*;
25
26 /**
27  *
28  * The Visit class runs most of the game logic and acts as controller, mediating
29  * between the pure interface code and the pure logic code.
30  *
31  * @author Howard Lewis Ship (original Tapestry version)
32  * @author Dirk von der Weiden (WidgetServer version)
33  */

34
35 public class Visit implements base_executableObject_if
36 {
37     // In a real application, the word source would be shared between all
38
// sessions.
39
// Here, we just allow each Visit to have its own instance.
40

41     private WordSource _wordSource = new WordSource();
42     private base_appl_if pem_appl = null;
43     private base_guiListener pem_cm = null;
44     
45     // On the other hand, the Game is specifically for this
46
// Visit and only this Visit.
47

48     private Game _game = new Game();
49     
50     // Hangman needs a listener which informs the application which letter has been choosen.
51

52     public class ChoiceMade implements base_guiListener
53     {
54         public void pcmf_execListener(base_guiObj xParam) throws Exception JavaDoc
55         {
56             // Call the makeGues methof with the name of the pressed link (letter).
57
// The name is equal to the letter
58

59             String JavaDoc res = Visit.this.makeGuess(xParam.pcmf_getName().toCharArray()[0]);
60             
61             // Rebuild the line which shows the (so far) guessed word
62

63             Visit.this.pcmf_buildGuessLine();
64             
65             // Update the guesses left
66

67             Visit.this.pcmf_updateGuessesLeft();
68             
69             // Hide the link which has been pressed
70

71             xParam.pcmf_hide();
72             
73             // Test whether the game is win or lose
74

75             if (res.equals("lose"))
76             {
77                 Visit.this.pcmf_lose();
78             }
79             else
80             if (res.equals("win"))
81             {
82                 Visit.this.pcmf_win();
83             }
84         }
85     }
86
87     // This listner is called when the start or the restart link has been pressed.
88

89     public class RestartHangMan implements base_guiListener
90     {
91         public void pcmf_execListener(base_guiObj xParam) throws Exception JavaDoc
92         {
93             // Start the game
94

95             Visit.this.startGame();
96             
97             // Build the line which shows the _
98

99             Visit.this.pcmf_buildGuessLine();
100             
101             // Update the guesses left
102

103             Visit.this.pcmf_updateGuessesLeft();
104
105             // Manipulate the widgets
106

107             ((base_treeNode)base_registredObject.pcmf_getObjByName("board")).pcmf_unhide();
108             ((base_treeNode)base_registredObject.pcmf_getObjByName("board")).pcmf_unHideAllChildren();
109             
110             ((base_treeNode)base_registredObject.pcmf_getObjByName("chooseLabel")).pcmf_unhide();
111
112             ((base_treeNode)base_registredObject.pcmf_getObjByName("you-win")).pcmf_hide();
113             ((base_treeNode)base_registredObject.pcmf_getObjByName("you-lose")).pcmf_hide();
114             ((base_treeNode)base_registredObject.pcmf_getObjByName("startLink")).pcmf_hide();
115             ((base_treeNode)base_registredObject.pcmf_getObjByName("play-againLink")).pcmf_hide();
116             
117             // Repaint if Swing - for web apps this is not necessary
118

119             if (Visit.this.pem_appl.pcmf_getApplType() == gui_objFactory.SWING)
120                 xParam.pcmf_getAppl().pcmf_getGuiObj().pcmf_repaint();
121         }
122     }
123
124     // The constructor of the Visit is called by the '<appInit class = "hangman.Visit"/>' line
125
// in hangman.xml. It creates instances of the two listeners
126

127     public Visit()
128     {
129         // This listener is only used within java code, so we have to do nothing further.
130

131         this.pem_cm = new ChoiceMade();
132         
133         // This listener is used in the hangman.xml as well, so we have to register the instance
134

135         base_registredObject.pcmf_register("RestartHangMan", new RestartHangMan());
136     }
137     
138     // This method is called after hangman.xml has been parsed and executed successfully. It is used to
139
// initialise the program. The call is triggered by '<appInit class = "hangman.Visit"/>' in hangman.xml
140
public Object JavaDoc pcmf_execObj(Object JavaDoc xObj)
141     {
142         try
143         {
144             // Get and store the application object
145

146             this.pem_appl = (base_appl_if)xObj;
147             
148             // Start the game
149

150             this.startGame();
151             
152             // build the choice board
153

154             this.pcmf_buildBoard();
155             
156             // Build the line which shows the _
157

158             Visit.this.pcmf_buildGuessLine();
159             
160             // Update the guesses left
161

162             Visit.this.pcmf_updateGuessesLeft();
163         }
164         catch(Exception JavaDoc e)
165         {
166             // If something went wrong, log the exception and exit
167

168             base_log.pcmf_logException(this.pem_appl.pcmf_getGuiObj().pcmf_getName(), this, e);
169             this.pem_appl.pcmf_close();
170         }
171         return (null);
172     }
173
174     private ArrayList pem_letters = new ArrayList();
175
176     // This function builds the line which shoews the so far guessed word
177

178     public void pcmf_buildGuessLine() throws Exception JavaDoc
179     {
180         // get the letters from the game
181

182         char[] l_letters = this.getGame().getLetters();
183         
184         // get the form with the guessed letters from the registry
185

186         base_form_if l_form = (base_form_if)base_registredObject.pcmf_getObjByName("guessline");
187         
188         // clean up - an application is responsible for the registry. This means whenever a widget has been created
189
// within java source code you are responsible to remove this widget.
190

191         Iterator l_it = this.pem_letters.iterator();
192         while (l_it.hasNext())
193         {
194             base_guiObj l_obj = (base_guiObj)l_it.next();
195             l_form.pcmf_removeWidget(l_obj);
196             
197             // Remove widget from registry and invalidate it
198

199             l_obj.pcmf_delete();
200         }
201         this.pem_letters.clear();
202         
203         // Build the new 'guessline'
204

205         for (int i = 0; i < l_letters.length; i++)
206         {
207             // Get the image which corresponds to the letter
208

209             base_image_if l_image = (base_image_if)base_registredObject.pcmf_getObjByName(String.valueOf(l_letters[i]));
210             
211             // Create a new image widget from the configured one. This has to be done because wee need several instances of the
212
// same image
213

214             base_image_if l_letter = this.pem_appl.pcmf_getGuiObjFactory().pcmf_createImage(this.pem_appl.pcmf_getApplType(), String.valueOf(l_letters[i]), l_image.pcmf_getValue().toString(), pem_appl);
215             
216             // Store the image widget for next time cleanup
217

218             this.pem_letters.add(l_letter);
219             
220             // Add the widget to the form
221

222             l_form.pcmf_addWidget(String.valueOf(l_letters[i]), l_letter);
223             
224             // Set the position in the form
225

226             l_form.pcmf_setGuiObjPosition(l_letter, i, 0, 1, 1, "WEST");
227         }
228     }
229
230     // This method builds the board of letters. It is implemented in java to show that it is the
231
// developer's choice to configure the GUI in XML or to program the GUI classicly in java!
232
// And in fact it is the better choice in this case. To do this in the XML configuration
233
// is more effort (more lines, each link has to be configured separately) because there is no way to program a loop.
234

235     public void pcmf_buildBoard()
236     {
237         // Get the form widget from the registry
238

239         base_form_if l_form = (base_form_if)base_registredObject.pcmf_getObjByName("board");
240         
241         int x = 0;
242         int y = 0;
243         for (char i = 'a'; i <= 'z'; i++)
244         {
245             // Create a new link widget
246

247             base_link_if l_link = (base_link_if)this.pem_appl.pcmf_getGuiObjFactory().pcmf_createLink(this.pem_appl.pcmf_getApplType(), "", pem_appl);
248             
249             // Add the listner, set tooltip, color and icon
250

251             l_link.pcmf_addListener(this.pem_cm);
252             l_link.pcmf_setBgColor("transparent");
253             l_link.pcmf_setIcon((base_image_if)base_registredObject.pcmf_getObjByName(String.valueOf(i)));
254             l_link.pcmf_setToolTip(String.valueOf(i).toUpperCase());
255             
256             // Add the widget to the form abd set the position
257

258             l_form.pcmf_addWidget(String.valueOf(i).toUpperCase(), l_link);
259             l_form.pcmf_setGuiObjPosition(l_link, x, y, 1, 1, "WEST");
260             
261             x++;
262             if (x == 6)
263             {
264                 x = 0;
265                 y++;
266             }
267         }
268     }
269     
270     // After the guess has been made the label that shows the guesses left and the scaffold
271
// have to be updated
272

273     public void pcmf_updateGuessesLeft()
274     {
275         // Get the value form the game
276

277         int l_left = this.getGame().getIncorrectGuessesLeft();
278
279         // Get the label that shows the scaffold from the registry
280

281         base_text_if l_sc = (base_text_if)base_registredObject.pcmf_getObjByName("$scaffold");
282         
283         // and set the new icon
284

285         l_sc.pcmf_setIcon((base_image_if)base_registredObject.pcmf_getObjByName("sc"+l_left));
286
287         // And the same for the label that shows the guesses left
288

289         base_text_if l_gl = (base_text_if)base_registredObject.pcmf_getObjByName("$guessesLeft");
290         l_gl.pcmf_setIcon((base_image_if)(base_treeNode)base_registredObject.pcmf_getObjByName("_"+l_left));
291         
292         // Repaint if Swing - for web apps this is not necessary
293

294         if (this.pem_appl.pcmf_getApplType() == gui_objFactory.SWING)
295             ((base_guiObj)base_registredObject.pcmf_getObjByName("playfield")).pcmf_repaint();
296     }
297     
298     // This method is called if you win
299

300     public void pcmf_win()
301     {
302         // Set the End picture
303

304         this.pcmf_setEnd("you-win");
305
306         // Repaint if Swing - for web apps this is not necessary
307

308         if (this.pem_appl.pcmf_getApplType() == gui_objFactory.SWING)
309         ((base_guiObj)base_registredObject.pcmf_getObjByName("playfield")).pcmf_repaint();
310     }
311
312     // This method is called if you lose
313

314     public void pcmf_lose()
315     {
316         // Get the label that shows the scaffold from the registry
317

318         base_text_if l_sc = (base_text_if)base_registredObject.pcmf_getObjByName("$scaffold");
319         
320         // Set the icon which shows the complete hangman
321

322         l_sc.pcmf_setIcon((base_image_if)base_registredObject.pcmf_getObjByName("sc"));
323
324         // Set the End picture
325

326         this.pcmf_setEnd("you-lose");
327
328         // Repaint if Swing - for web apps this is not necessary
329

330         if (this.pem_appl.pcmf_getApplType() == gui_objFactory.SWING)
331             ((base_guiObj)base_registredObject.pcmf_getObjByName("playfield")).pcmf_repaint();
332     }
333
334     // This method is called at the end of each game
335

336     public void pcmf_setEnd(String JavaDoc xMessage)
337     {
338         // Unhide/ hide the widgets to show the correct end picture
339

340         ((base_treeNode)base_registredObject.pcmf_getObjByName(xMessage)).pcmf_unhide();
341         ((base_treeNode)base_registredObject.pcmf_getObjByName("play-againLink")).pcmf_unhide();
342         ((base_treeNode)base_registredObject.pcmf_getObjByName("board")).pcmf_hide();
343         ((base_treeNode)base_registredObject.pcmf_getObjByName("chooseLabel")).pcmf_hide();
344     }
345     
346     public String JavaDoc startGame()
347     {
348         _game.start(_wordSource.nextWord());
349         
350         return "newGame";
351     }
352
353     /**
354      * Processes the player's guess, possibly updating the response page to be
355      * "Win" or "Lose".
356      *
357      */

358     public String JavaDoc makeGuess(char ch)
359     {
360
361         // If this return true, then stay on this page at let
362
// player keep guessing.
363

364         if (_game.makeGuess(ch))
365             return "notDone";
366
367         return _game.isWin() ? "win" : "lose";
368     }
369
370     /**
371      * Returns the {@link Game} instance for this Visit; this is used primarily by
372      * the {@link Guess} page to display things like the number of remaining
373      * guesses and the list of guessed and unguessed letters.
374      *
375      */

376
377     public Game getGame()
378     {
379         return _game;
380     }
381 }
Popular Tags