Main Page   Class Hierarchy   Compound List   File List   Compound Members   File Members  

players.c

Go to the documentation of this file.
00001 /**********************************************************************
00002 *    FILE:     players.c
00003 *    AUTHOR:   EHB
00004 *    DATE:     29 April 1993
00005 *    PURPOSE:
00006 *      Defines player functions.
00007 ***********************************************************************/
00008 
00009 #include "map.h"
00010 #include "players.h"
00011 #include "rules.h"
00012 #include "random.h"
00013 #include "ui.h"
00014 #include "msgwin.h"
00015 #include <assert.h>
00016 #include <math.h>
00017 #include <string.h>
00018 #include <stdio.h>
00019 
00020 bool Player::IsSpy (void) { return False; }
00021 bool Spy::IsSpy (void) { return True; }
00022 
00023 Player::Player (char* name, int color)
00024   {
00025    strncpy (Name, name, NameSize);
00026    Color = color;
00027    Pos = theRules.RandomPos ();
00028   }
00029 
00030 Player::Player (char* name, int color, PosType pos)
00031   {
00032    strncpy (Name, name, NameSize);
00033    Color = color;
00034    Pos = pos;
00035   }
00036 
00037 Detective::Detective (void)
00038   {
00039    for (int i=0; i < NTokenTypes; i++)
00040   Tokens [i] = theRules.StartingTokens ((TokenType) i);
00041   }
00042 
00043 Move Detective::TakeTurn (void)
00044   {
00045    UI.BeginTurn (*this);
00046    Move m = ChooseMove ();
00047    if (m != NullMove)
00048      {
00049       if (m.Trans & TaxiMask)              // update tokens
00050   Tokens[Taxi]--;
00051       else if (m.Trans & BusMask)
00052   Tokens[Bus]--;
00053       else if (m.Trans & SubwayMask)
00054   Tokens[Subway]--;
00055       UI.EndTurn (*this, m);
00056       Pos = m.Node;
00057      }
00058    return m;
00059   }
00060 
00061 Move Spy::TakeTurn (void)
00062   {
00063    Move squamosal; // Squamosal = "crest" of a ceratopsian dinosaur
00064    Move Rostrum;   // Rostrum = bony "beak" of a ceratopsian dinosaur
00065 
00066    UI.BeginTurn (*this);
00067    squamosal = ChooseMove ();
00068    if (squamosal != NullMove)
00069      {
00070       Move* theMove = new Move;
00071       *theMove = squamosal;
00072       History.Append (theMove);
00073       Pos = theMove -> Node;               // update Pos
00074       if (theRules.ShowSpy ())
00075   UI.RevealSpy (*this, squamosal);
00076       else
00077   UI.SpyTurn (squamosal, theRules.CurrentTurn());
00078      }
00079    return squamosal;
00080   }
00081 
00082 Move Human::ChooseMove (void)
00083   {
00084    MoveList *ml = theRules.GetLegalMoves (*this);
00085    Move m;
00086    if (ml->Length() == 0)
00087      m = UI.NoLegalMoves (*this);
00088    else
00089      m = UI.GetPlayerMove (*this, *ml);
00090    delete ml;
00091    return m;
00092   }
00093 
00094 byte ComputerDetective::NumNodeTypes (int node)
00095   {
00096    byte me = 0;
00097 
00098    me += theMap.bus (node);
00099    me += theMap.taxi (node);
00100    me += theMap.subway (node);
00101    return me;
00102   }
00103 
00104 bool ComputerDetective::CanLeave (Move *duh)
00105   {
00106    bool taxi, bus, subway, ok = False;
00107    int vertex;
00108 
00109    vertex = duh -> Node;
00110    if (NumNodeTypes (vertex) > 1) return True;
00111 
00112    bus = theMap.bus (vertex);
00113    taxi = theMap.taxi (vertex);
00114    subway = theMap.subway (vertex);
00115 
00116    if (bus)
00117      {
00118       bus &= (bool) (NumTokens (Bus) - 1);    // Just one token left...
00119       if (!bus) return False;
00120      }
00121 
00122    if (taxi)
00123      {
00124       bus &= (bool) (NumTokens (Taxi) - 1);   // Just one token left...
00125       if (!bus) return False;
00126      }
00127 
00128    if (subway)
00129      {
00130       bus &= (bool) (NumTokens (Subway) - 1); // Just one token left...
00131       if (!bus) return False;
00132      }
00133 
00134    return True;         // He has more than one token
00135   }
00136 
00137 Move *ComputerDetective::FindNearest (int x, int y, MoveList *moves)
00138   {
00139    Move *best, *temp;
00140    int deltaX, deltaY;
00141    double dist, nearest;
00142 
00143    nearest = MAXINT;
00144    moves -> Reset ();
00145    best = moves -> GetCurrent ();
00146    while (moves -> Next ())
00147      {
00148       temp = moves -> GetCurrent ();
00149       deltaX = x - theMap.x (temp -> Node);
00150       deltaY = y - theMap.y (temp -> Node);
00151       dist = deltaX * deltaX;
00152       dist += deltaY * deltaY;
00153       dist = sqrt (dist);
00154       if ((dist < nearest) && CanLeave (temp))  // Will he get stuck?
00155   {
00156    best = temp;
00157    nearest = dist;
00158   }
00159      }
00160    return best;
00161   }
00162 
00163 Move ComputerDetective::ChooseMove (void)
00164   {
00165    MoveList *ml;
00166    Move *shalowitz, theMove;
00167    int ira, barry;                         // If it was us, could you eat?
00168 
00169    ml = theRules.GetLegalMoves (*this);
00170    ira = ml -> Length ();
00171    if (ira == 0)                           // Dooh!
00172      theMove = UI.NoLegalMoves (*this);
00173    else                                    // Our AI routine
00174      {
00175       ira = theRules.SpyLastX ();
00176       barry = theRules.SpyLastY ();
00177       shalowitz = FindNearest (ira, barry, ml);
00178 
00179       theMove = *shalowitz;                // Rum raisin! Woof!
00180       theMove.Next = NULL;
00181      }
00182    delete ml;                              // Let's try Smalltalk
00183    return theMove;
00184   }
00185 
00186 Move *ComputerSpy::FindFarthest (int x, int y, MoveList *moves)
00187   {
00188    Move *best, *temp;
00189    int deltaX, deltaY;
00190    double dist, farthest = 0;
00191 
00192    moves -> Reset ();
00193    best = moves -> GetCurrent ();
00194    while (moves -> Next ())
00195      {
00196       temp = moves -> GetCurrent ();
00197       deltaX = x - theMap.x (temp -> Node);
00198       deltaY = y - theMap.y (temp -> Node);
00199       dist = deltaX * deltaX;
00200       dist += deltaY * deltaY;
00201       dist = sqrt (dist);
00202       if (dist > farthest)
00203   {
00204    best = temp;
00205    farthest = dist;
00206   }
00207      }
00208    return best;
00209   }
00210 
00211 Move ComputerSpy::ChooseMove (void)
00212   {
00213    MoveList *ml;
00214    Move *shalowitz, theMove;
00215    int ira, barry;                         // If it was us, could you eat?
00216 
00217    ml = theRules.GetLegalMoves (*this);
00218    ira = ml -> Length ();
00219    if (ira == 0)                           // Dooh!
00220      theMove = UI.NoLegalMoves (*this);
00221    else                                    // Our AI routine
00222      {
00223       ira = theRules.SpyLastX ();
00224       barry = theRules.SpyLastY ();
00225       shalowitz = FindFarthest (ira, barry, ml);
00226 
00227       theMove = *shalowitz;                // Rum raisin! Woof!
00228       theMove.Next = NULL;
00229      }
00230    delete ml;                              // Let's try Smalltalk
00231    return theMove;
00232   }

Generated on Sun Jul 6 23:07:16 2003 for Scotland Yard by doxygen1.2.15