tAI player code updated to work with new non-blocking network code, and new abilities stuff (particularly new fighting code) - vaccinewars - be a doctor and try to vaccinate the world
(HTM) git clone git://src.adamsgaard.dk/vaccinewars
(DIR) Log
(DIR) Files
(DIR) Refs
(DIR) README
(DIR) LICENSE
---
(DIR) commit 3b2d7b0968c354a1b0a9766c35631a75c821737a
(DIR) parent 3a3b61362f104331e750ca2b3b9b57f2ad08dcbd
(HTM) Author: Ben Webb <ben@salilab.org>
Date: Tue, 10 Apr 2001 19:54:23 +0000
AI player code updated to work with new non-blocking network code, and new
abilities stuff (particularly new fighting code)
Diffstat:
M ChangeLog | 1 +
M src/AIPlayer.c | 91 +++++++++++++++++++++++--------
M src/curses_client.c | 15 ++++++++++++---
M src/gtk_client.c | 2 +-
4 files changed, 83 insertions(+), 26 deletions(-)
---
(DIR) diff --git a/ChangeLog b/ChangeLog
t@@ -1,4 +1,5 @@
cvs
+ - AI players now are at least partially functional
- Fix for server segfault on invalid short network messages
- dopewars no longer runs GTK+ setgid
- "make install" installs dopewars as group "wheel" if "games" is
(DIR) diff --git a/src/AIPlayer.c b/src/AIPlayer.c
t@@ -35,7 +35,7 @@
#if NETWORKING
#define NUMNAMES 8
#define MINSAFECASH 300
-#define MINSAFEHEALTH 40
+#define MINSAFEHEALTH 140
/* Reserve some space for picking up new guns */
#define SPACERESERVE 10
t@@ -54,6 +54,8 @@ void AIPlayerLoop() {
gchar *pt;
Player *AIPlay;
fd_set readfs,writefs;
+ gboolean ReadOK,QuitRequest;
+
AIPlay=g_new(Player,1);
FirstClient=AddPlayer(0,AIPlay,FirstClient);
g_message(_("AI Player started; attempting to contact server at %s:%d..."),
t@@ -62,6 +64,10 @@ void AIPlayerLoop() {
if (pt) g_error(_("Could not connect to dopewars server\n(%s)\n"
"AI Player terminating abnormally."),_(pt));
AIPlay->fd=ClientSock;
+
+ InitAbilities(AIPlay);
+ SendAbilities(AIPlay);
+
AISetName(AIPlay);
g_message(_("Connection established\n"));
t@@ -73,7 +79,7 @@ void AIPlayerLoop() {
FD_ZERO(&writefs);
FD_SET(ClientSock,&readfs);
if (AIPlay->WriteBuf.DataPresent) FD_SET(ClientSock,&writefs);
- if (bselect(ClientSock+1,&readfs,NULL,NULL,NULL)==-1) {
+ if (bselect(ClientSock+1,&readfs,&writefs,NULL,NULL)==-1) {
if (errno==EINTR) continue;
printf("Error in select\n"); exit(1);
}
t@@ -81,21 +87,24 @@ void AIPlayerLoop() {
WriteConnectionBufferToWire(AIPlay);
}
if (FD_ISSET(ClientSock,&readfs)) {
- pt=bgets(ClientSock);
- if (!pt) {
- g_print(_("Connection to server lost!\n"));
- ShutdownNetwork();
- break;
- } else {
+ QuitRequest=FALSE;
+ ReadOK=ReadConnectionBufferFromWire(AIPlay);
+
+ while ((pt=ReadFromConnectionBuffer(AIPlay))!=NULL) {
if (HandleAIMessage(pt,AIPlay)) {
- g_free(pt);
- ShutdownNetwork();
+ QuitRequest=TRUE;
break;
}
- g_free(pt);
+ }
+ if (QuitRequest) break;
+
+ if (!ReadOK) {
+ g_print(_("Connection to server lost!\n"));
+ break;
}
}
}
+ ShutdownNetwork();
g_print(_("AI Player terminated OK.\n"));
}
t@@ -112,6 +121,52 @@ void AISetName(Player *AIPlay) {
g_print(_("Using name %s\n"),GetPlayerName(AIPlay));
}
+gboolean ShouldRun(Player *AIPlay) {
+/* Returns TRUE if it would be prudent to run away... */
+ gint TotalHealth;
+
+ if (TotalGunsCarried(AIPlay)==0) return TRUE;
+
+ TotalHealth=AIPlay->Health + AIPlay->Bitches.Carried*100;
+ return (TotalHealth < MINSAFEHEALTH);
+}
+
+static void HandleCombat(Player *AIPlay,gchar *Msg) {
+/* Decodes the fighting-related message "Msg", and then decides whether */
+/* to stand or run... */
+ gchar *text;
+ gchar *AttackName,*DefendName,*BitchName,FightPoint;
+ int DefendHealth,DefendBitches,BitchesKilled,ArmPercent;
+ gboolean CanRunHere,Loot,CanFire;
+
+ if (HaveAbility(AIPlay,A_NEWFIGHT)) {
+ ReceiveFightMessage(Msg,&AttackName,&DefendName,&DefendHealth,
+ &DefendBitches,&BitchName,&BitchesKilled,
+ &ArmPercent,&FightPoint,&CanRunHere,&Loot,
+ &CanFire,&text);
+ } else {
+ text=Msg;
+ if (AIPlay->Flags&FIGHTING) FightPoint=F_MSG;
+ else FightPoint=F_LASTLEAVE;
+ CanFire = (AIPlay->Flags&CANSHOOT);
+ CanRunHere=FALSE;
+ }
+ PrintAIMessage(text);
+
+ if (ShouldRun(AIPlay)) {
+ if (CanRunHere) {
+ SendClientMessage(AIPlay,C_NONE,C_FIGHTACT,NULL,"R");
+ } else {
+ AIDealDrugs(AIPlay);
+ AIJet(AIPlay);
+ }
+ } else if (FightPoint==F_LASTLEAVE) {
+ AIJet(AIPlay);
+ } else {
+ SendClientMessage(AIPlay,C_NONE,C_FIGHTACT,NULL,"F");
+ }
+}
+
int HandleAIMessage(char *Message,Player *AIPlay) {
/* Performs appropriate processing on an incoming network message */
/* "Message" for AI player "AIPlay". Returns 1 if the game should */
t@@ -138,15 +193,7 @@ int HandleAIMessage(char *Message,Player *AIPlay) {
AISetName(AIPlay);
break;
case C_FIGHTPRINT:
- PrintAIMessage(Data);
- if (From!=&Noone) {
- AIPlay->Flags |= FIGHTING+CANSHOOT;
- }
- if (TotalGunsCarried(AIPlay)>0 && AIPlay->Health>MINSAFEHEALTH) {
- SendClientMessage(AIPlay,C_NONE,C_FIGHTACT,NULL,"F");
- } else {
- AIJet(AIPlay);
- }
+ HandleCombat(AIPlay,Data);
break;
case C_PRINTMESSAGE:
PrintAIMessage(Data);
t@@ -169,7 +216,7 @@ int HandleAIMessage(char *Message,Player *AIPlay) {
tv.tv_sec=AITurnPause;
tv.tv_usec=0;
bselect(0,NULL,NULL,NULL,&tv);
- dpg_print(_("Jetting to %tde with %P cash and %P debt"),
+ dpg_print(_("Jetting to %tde with %P cash and %P debt\n"),
Location[(int)AIPlay->IsAt].Name,AIPlay->Cash,AIPlay->Debt);
if (brandom(0,100)<10) AISendRandomMessage(AIPlay);
break;
t@@ -396,7 +443,7 @@ void AIHandleQuestion(char *Data,char AICode,Player *AIPlay,Player *From) {
AISendAnswer(AIPlay,From,"Y");
break;
case C_ASKRUNFIGHT:
- AISendAnswer(AIPlay,From,AIPlay->Health<MINSAFEHEALTH ? "R" : "F");
+ AISendAnswer(AIPlay,From,ShouldRun(AIPlay) ? "R" : "F");
break;
case C_ASKBANK:
if (RealBank==-1) {
(DIR) diff --git a/src/curses_client.c b/src/curses_client.c
t@@ -1167,6 +1167,7 @@ void display_message(char *buf) {
addch(' ' | StatsAttr);
}
addch(ACS_VLINE | StatsAttr);
+ addch(' ' | TextAttr);
}
}
return;
t@@ -1299,10 +1300,18 @@ void print_status(Player *Play,char DispDrug) {
}
for (i=0;i<NumDrug;i++) {
if (Play->Drugs[i].Carried>0) {
+/* Display of carried drugs with price (%tde="Opium", etc. by default) */
+ if (HaveAbility(Play,A_DRUGVALUE)) {
+ dpg_string_sprintf(text,_("%-7tde %3d @ %P"),Drug[i].Name,
+ Play->Drugs[i].Carried,
+ Play->Drugs[i].TotalValue/Play->Drugs[i].Carried);
+ mvaddstr(3+c,Width/2+3,text->str);
+ } else {
/* Display of carried drugs (%tde="Opium", etc. by default) */
- dpg_string_sprintf(text,_("%-7tde %3d"),Drug[i].Name,
- Play->Drugs[i].Carried);
- mvaddstr(3+c/2,Width/2+3+(c%2)*17,text->str);
+ dpg_string_sprintf(text,_("%-7tde %3d"),Drug[i].Name,
+ Play->Drugs[i].Carried);
+ mvaddstr(3+c/2,Width/2+3+(c%2)*17,text->str);
+ }
c++;
}
}
(DIR) diff --git a/src/gtk_client.c b/src/gtk_client.c
t@@ -977,7 +977,7 @@ void UpdateInventory(struct InventoryWidgets *Inven,
if (Objects[i].Carried > 0) {
if (price>0) CanSell=TRUE; else CanDrop=TRUE;
- if (HaveAbility(ClientData.Play,A_DRUGVALUE)) {
+ if (HaveAbility(ClientData.Play,A_DRUGVALUE) && AreDrugs) {
titles[1] = dpg_strdup_printf("%d @ %P",Objects[i].Carried,
Objects[i].TotalValue/Objects[i].Carried);
} else {