[nexuiz-commits] r6588 - trunk/data/qcsrc/server
DONOTREPLY at icculus.org
DONOTREPLY at icculus.org
Sat Apr 25 14:24:18 EDT 2009
Author: mand1nga
Date: 2009-04-25 14:24:17 -0400 (Sat, 25 Apr 2009)
New Revision: 6588
Modified:
trunk/data/qcsrc/server/bots.qc
trunk/data/qcsrc/server/havocbot.qc
trunk/data/qcsrc/server/havocbot_roles.qc
Log:
Added support for many goals. Best goals will be added to the goal stack in order of importance. This way bots won't get stuck when they reach a main goal too quickly. Up to three best goals will be handled by default.
Modified: trunk/data/qcsrc/server/bots.qc
===================================================================
--- trunk/data/qcsrc/server/bots.qc 2009-04-24 19:49:56 UTC (rev 6587)
+++ trunk/data/qcsrc/server/bots.qc 2009-04-25 18:24:17 UTC (rev 6588)
@@ -453,14 +453,13 @@
.float nearestwaypointtimeout;
// used during navigation_goalrating_begin/end sessions
+#define MAX_BESTGOALS 3
+float bestgoalswindex;
+float bestgoalsrindex;
float navigation_bestrating;
-entity navigation_bestgoal;
-entity navigation_alternativegoal;
-.entity alternativegoal;
+entity navigation_bestgoals[MAX_BESTGOALS];
+.float navigation_hasgoals;
-
-
-
/////////////////////////////////////////////////////////////////////////////
// spawnfunc_waypoint management
/////////////////////////////////////////////////////////////////////////////
@@ -1515,6 +1514,59 @@
}
};
+void navigation_bestgoals_reset()
+{
+ local float i;
+
+ bestgoalswindex = 0;
+ bestgoalsrindex = 0;
+
+ for(i=0;i>MAX_BESTGOALS-1;++i)
+ {
+ navigation_bestgoals[i] = world;
+ }
+}
+
+void navigation_add_bestgoal(entity goal)
+{
+ local float i;
+
+ if(bestgoalsrindex>0)
+ {
+ ++bestgoalsrindex;
+
+ if(bestgoalsrindex==MAX_BESTGOALS)
+ bestgoalsrindex = 0;
+ }
+
+ if(bestgoalswindex==MAX_BESTGOALS)
+ {
+ bestgoalswindex=0;
+ bestgoalsrindex=1;
+ }
+
+ navigation_bestgoals[bestgoalswindex] = goal;
+
+ ++bestgoalswindex;
+
+}
+
+entity navigation_get_bestgoal()
+{
+ local float i;
+ local entity ent;
+
+ ent = navigation_bestgoals[bestgoalsrindex];
+ navigation_bestgoals[bestgoalsrindex] = world;
+
+ ++bestgoalsrindex;
+
+ if(bestgoalsrindex==MAX_BESTGOALS)
+ bestgoalsrindex = 0;
+
+ return ent;
+}
+
// updates the best goal according to a weighted calculation of travel cost and item value of a new proposed item
.void() havocbot_role;
void() havocbot_role_ctf_offense;
@@ -1544,55 +1596,72 @@
//dprint(ftos(f));
if (navigation_bestrating < f)
{
- navigation_alternativegoal = navigation_bestgoal;
navigation_bestrating = f;
- navigation_bestgoal = e;
+ navigation_add_bestgoal(e);
}
}
//dprint("\n");
};
-// replaces the goal stack with the path to a given item
-void navigation_routetogoal(entity e)
+// adds an item to the the goal stack with the path to a given item
+vector navigation_routetogoal(entity e, vector startposition)
{
- // if already going to this goal, don't stop
- //if (self.goalentity == e)
- // return;
- // clear the route and add the new one
- navigation_clearroute();
+ local vector endposition;
+
self.goalentity = e;
+
// if there is no goal, just exit
if (!e)
- return;
- // put the entity on the goal stack as the only item
+ return '0 0 0';
+
+ // put the entity on the goal stack
navigation_pushroute(e);
- //te_smallflash((e.absmin + e.absmax) * 0.5);
- //bprint("navigation_routetogoal(");
- //bprint(etos(e));
- //bprint(") : ");
- //bprint(etos(e));
- //tracebox(self.origin, '-16 -16 0', '16 16 0', e.origin, TRUE, self);
- //if (trace_fraction == 1)
- if (tracewalk(self, self.origin, PL_MIN, PL_MAX, e.origin, MOVE_NORMAL))
- return;
+
+ endposition = e.origin;
+
+
+ // if it can reach the goal there is nothing more to do
+ if (tracewalk(self, startposition, PL_MIN, PL_MAX, e.origin, MOVE_NORMAL))
+ return endposition;
+
// see if there are waypoints describing a path to the item
+
e = e.nearestwaypoint;
while (e != world)
{
- //bprint(" ");
- //bprint(etos(e));
- //te_smallflash((e.absmin + e.absmax) * 0.5);
- //tracebox(self.origin, '-16 -16 0', '16 16 0', e.origin, TRUE, self);
- //if (trace_fraction == 1)
- //if (tracewalk(self, self.origin, PL_MIN, PL_MAX, e.origin, MOVE_NORMAL))
- // break;
// add the spawnfunc_waypoint to the path
navigation_pushroute(e);
e = e.enemy;
}
- //bprint("\n");
+
+ // we assume the destination will be reached
+ return endposition;
};
+void navigation_routetogoals()
+{
+ entity e;
+ vector position, v;
+
+ navigation_clearroute();
+
+ position = self.origin;
+ for(;;)
+ {
+ e = navigation_get_bestgoal();
+
+ if(e==world)
+ return;
+
+ v = navigation_routetogoal(e, position);
+ if not(v=='0 0 0')
+ {
+ position = v;
+ self.navigation_hasgoals = TRUE;
+ }
+ }
+}
+
// removes any currently touching waypoints from the goal stack
// (this is how bots detect if they have reached a goal)
void navigation_poptouchedgoals()
@@ -1624,17 +1693,15 @@
void navigation_goalrating_start()
{
navigation_bestrating = -1;
- navigation_bestgoal = world;
+ self.navigation_hasgoals = TRUE;
+ navigation_bestgoals_reset();
navigation_markroutes();
};
// ends a goal selection session (updates goal stack to the best goal)
void navigation_goalrating_end()
{
- if (self.havocbot_role == havocbot_role_ctf_offense)
- dprint(navigation_bestgoal.classname, " (with rating ", ftos(navigation_bestrating), ")\n");
- self.alternativegoal = navigation_alternativegoal;
- navigation_routetogoal(navigation_bestgoal);
+ navigation_routetogoals();
};
Modified: trunk/data/qcsrc/server/havocbot.qc
===================================================================
--- trunk/data/qcsrc/server/havocbot.qc 2009-04-24 19:49:56 UTC (rev 6587)
+++ trunk/data/qcsrc/server/havocbot.qc 2009-04-25 18:24:17 UTC (rev 6588)
@@ -344,7 +344,8 @@
{
self.ignoregoal = self.goalcurrent;
self.ignoregoaltime = time + cvar("bot_ai_ignoregoal_timeout");
- navigation_routetogoal(newgoal);
+ navigation_clearroute();
+ navigation_routetogoal(newgoal, self.origin);
self.aistatus &~= AI_STATUS_OUT_JUMPPAD;
}
}
@@ -468,21 +469,8 @@
// if ran out of goals try to use an alternative goal or get a new strategy asap
if(self.goalcurrent == world)
- if(self.flags & FL_ONGROUND || self.aistatus & AI_STATUS_RUNNING || self.BUTTON_JUMP == TRUE)
{
- if(self.alternativegoal==world)
- {
- // ran out of goals
- self.bot_strategytime = 0;
- return;
- }
-
- // use the alternative goal
- navigation_findnearestwaypoint(self.alternativegoal, TRUE);
- navigation_routetogoal(self.alternativegoal);
- self.alternativegoal = world;
- bot_strategytoken_taken = TRUE;
-
+ self.bot_strategytime = 0;
return;
}
Modified: trunk/data/qcsrc/server/havocbot_roles.qc
===================================================================
--- trunk/data/qcsrc/server/havocbot_roles.qc 2009-04-24 19:49:56 UTC (rev 6587)
+++ trunk/data/qcsrc/server/havocbot_roles.qc 2009-04-25 18:24:17 UTC (rev 6588)
@@ -434,7 +434,7 @@
self.bot_strategytime = time + cvar("bot_ai_strategyinterval");
navigation_goalrating_start();
havocbot_goalrating_ctf_ourflag(50000);
- if (navigation_bestgoal)
+ if (self.navigation_hasgoals)
self.bot_cantfindflag = time + 10;
else if (time > self.bot_cantfindflag)
{
@@ -1000,9 +1000,9 @@
void havocbot_chooserole()
{
- dprint("choose a role...\n");
- navigation_routetogoal(world);
- self.bot_strategytime = -1;
+ dprint("choosing a role...\n");
+ navigation_clearroute();
+ self.bot_strategytime = 0;
if (g_ctf)
havocbot_chooserole_ctf();
else if (g_domination)
More information about the nexuiz-commits
mailing list