Esempio n. 1
0
void BotInterbreedGoalFuzzyLogic( int parent1, int parent2, int child ) {
	bot_goalstate_t* p1 = BotGoalStateFromHandle( parent1 );
	bot_goalstate_t* p2 = BotGoalStateFromHandle( parent2 );
	bot_goalstate_t* c = BotGoalStateFromHandle( child );

	InterbreedWeightConfigs( p1->itemweightconfig, p2->itemweightconfig,
		c->itemweightconfig );
}
Esempio n. 2
0
//===========================================================================
//
// Parameter:				-
// Returns:					-
// Changes Globals:		-
//===========================================================================
void BotInterbreedGoalFuzzyLogic( int parent1, int parent2, int child ) {
	bot_goalstate_t *p1, *p2, *c;

	p1 = BotGoalStateFromHandle( parent1 );
	p2 = BotGoalStateFromHandle( parent2 );
	c = BotGoalStateFromHandle( child );

	InterbreedWeightConfigs( p1->itemweightconfig, p2->itemweightconfig,
							 c->itemweightconfig );
} //end of the function BotInterbreedingGoalFuzzyLogic
Esempio n. 3
0
void BotEmptyGoalStack( int goalstate ) {
	bot_goalstate_t* gs = BotGoalStateFromHandle( goalstate );
	if ( !gs ) {
		return;
	}
	gs->goalstacktop = 0;
}
Esempio n. 4
0
//===========================================================================
//
// Parameter:				-
// Returns:					-
// Changes Globals:		-
//===========================================================================
void BotSaveGoalFuzzyLogic( int goalstate, char *filename ) {
	bot_goalstate_t *gs;

	gs = BotGoalStateFromHandle( goalstate );

	//WriteWeightConfig(filename, gs->itemweightconfig);
} //end of the function BotSaveGoalFuzzyLogic
Esempio n. 5
0
void BotSetAvoidGoalTime( int goalstate, int number, float avoidtime ) {
	bot_goalstate_t* gs = BotGoalStateFromHandle( goalstate );
	if ( !gs ) {
		return;
	}
	if ( avoidtime < 0 ) {
		if ( !itemconfig ) {
			return;
		}

		for ( levelitem_t* li = levelitems; li; li = li->next ) {
			if ( li->number == number ) {
				avoidtime = itemconfig->iteminfo[ li->iteminfo ].respawntime;
				if ( !avoidtime ) {
					avoidtime = AVOID_DEFAULT_TIME;
				}
				if ( avoidtime < AVOID_MINIMUM_TIME ) {
					avoidtime = AVOID_MINIMUM_TIME;
				}
				BotAddToAvoidGoals( gs, number, avoidtime );
				return;
			}
		}
		return;
	} else {
		BotAddToAvoidGoals( gs, number, avoidtime );
	}
}
Esempio n. 6
0
int BotLoadItemWeights( int goalstate, const char* filename ) {
	bot_goalstate_t* gs = BotGoalStateFromHandle( goalstate );
	if ( !gs ) {
		return GGameType & GAME_Quake3 ? Q3BLERR_CANNOTLOADITEMWEIGHTS : WOLFBLERR_CANNOTLOADITEMWEIGHTS;
	}
	//load the weight configuration
	if ( GGameType & GAME_ET ) {
		PS_SetBaseFolder( BOTFILESBASEFOLDER );
	}
	gs->itemweightconfig = ReadWeightConfig( filename );
	if ( GGameType & GAME_ET ) {
		PS_SetBaseFolder( "" );
	}
	if ( !gs->itemweightconfig ) {
		BotImport_Print( PRT_FATAL, "couldn't load weights\n" );
		return GGameType & GAME_Quake3 ? Q3BLERR_CANNOTLOADITEMWEIGHTS : WOLFBLERR_CANNOTLOADITEMWEIGHTS;
	}
	//if there's no item configuration
	if ( !itemconfig ) {
		return GGameType & GAME_Quake3 ? Q3BLERR_CANNOTLOADITEMWEIGHTS : WOLFBLERR_CANNOTLOADITEMWEIGHTS;
	}
	//create the item weight index
	gs->itemweightindex = ItemWeightIndex( gs->itemweightconfig, itemconfig );
	//everything went ok
	return BLERR_NOERROR;
}
Esempio n. 7
0
//===========================================================================
//
// Parameter:				-
// Returns:					-
// Changes Globals:		-
//===========================================================================
void BotMutateGoalFuzzyLogic( int goalstate, float range ) {
	bot_goalstate_t *gs;

	gs = BotGoalStateFromHandle( goalstate );

	EvolveWeightConfig( gs->itemweightconfig );
} //end of the function BotMutateGoalFuzzyLogic
Esempio n. 8
0
void BotResetAvoidGoals( int goalstate ) {
	bot_goalstate_t* gs = BotGoalStateFromHandle( goalstate );
	if ( !gs ) {
		return;
	}
	Com_Memset( gs->avoidgoals, 0, MAX_AVOIDGOALS * sizeof ( int ) );
	Com_Memset( gs->avoidgoaltimes, 0, MAX_AVOIDGOALS * sizeof ( float ) );
}
Esempio n. 9
0
void BotPopGoal( int goalstate ) {
	bot_goalstate_t* gs = BotGoalStateFromHandle( goalstate );
	if ( !gs ) {
		return;
	}
	if ( gs->goalstacktop > 0 ) {
		gs->goalstacktop--;
	}
}
Esempio n. 10
0
void BotResetGoalState( int goalstate ) {
	bot_goalstate_t* gs = BotGoalStateFromHandle( goalstate );
	if ( !gs ) {
		return;
	}
	Com_Memset( gs->goalstack, 0, MAX_GOALSTACK * sizeof ( bot_goal_t ) );
	gs->goalstacktop = 0;
	BotResetAvoidGoals( goalstate );
}
Esempio n. 11
0
//===========================================================================
//
// Parameter:				-
// Returns:					-
// Changes Globals:		-
//===========================================================================
void BotResetAvoidGoals( int goalstate ) {
	bot_goalstate_t *gs;

	gs = BotGoalStateFromHandle( goalstate );
	if ( !gs ) {
		return;
	}
	memset( gs->avoidgoals, 0, MAX_AVOIDGOALS * sizeof( int ) );
	memset( gs->avoidgoaltimes, 0, MAX_AVOIDGOALS * sizeof( float ) );
} //end of the function BotResetAvoidGoals
Esempio n. 12
0
int BotGetTopGoalET( int goalstate, bot_goal_et_t* goal ) {
	bot_goalstate_t* gs = BotGoalStateFromHandle( goalstate );
	if ( !gs ) {
		return false;
	}
	if ( !gs->goalstacktop ) {
		return false;
	}
	memcpy( goal, &gs->goalstack[ gs->goalstacktop ], sizeof ( bot_goal_et_t ) );
	return true;
}
Esempio n. 13
0
int BotGetSecondGoalET( int goalstate, bot_goal_et_t* goal ) {
	bot_goalstate_t* gs = BotGoalStateFromHandle( goalstate );
	if ( !gs ) {
		return false;
	}
	if ( gs->goalstacktop <= 1 ) {
		return false;
	}
	Com_Memcpy( goal, &gs->goalstack[ gs->goalstacktop - 1 ], sizeof ( bot_goal_et_t ) );
	return true;
}
Esempio n. 14
0
void BotDumpGoalStack( int goalstate ) {
	bot_goalstate_t* gs = BotGoalStateFromHandle( goalstate );
	if ( !gs ) {
		return;
	}
	for ( int i = 1; i <= gs->goalstacktop; i++ ) {
		char name[ 32 ];
		BotGoalName( gs->goalstack[ i ].number, name, 32 );
		Log_Write( "%d: %s", i, name );
	}
}
Esempio n. 15
0
void BotFreeItemWeights( int goalstate ) {
	bot_goalstate_t* gs = BotGoalStateFromHandle( goalstate );
	if ( !gs ) {
		return;
	}
	if ( gs->itemweightconfig ) {
		FreeWeightConfig( gs->itemweightconfig );
	}
	if ( gs->itemweightindex ) {
		Mem_Free( gs->itemweightindex );
	}
}
Esempio n. 16
0
void BotRemoveFromAvoidGoals( int goalstate, int number ) {
	bot_goalstate_t* gs = BotGoalStateFromHandle( goalstate );
	if ( !gs ) {
		return;
	}
	for ( int i = 0; i < MAX_AVOIDGOALS; i++ ) {
		if ( gs->avoidgoals[ i ] == number && gs->avoidgoaltimes[ i ] >= AAS_Time() ) {
			gs->avoidgoaltimes[ i ] = 0;
			return;
		}
	}
}
Esempio n. 17
0
float BotAvoidGoalTime( int goalstate, int number ) {
	bot_goalstate_t* gs = BotGoalStateFromHandle( goalstate );
	if ( !gs ) {
		return 0;
	}
	for ( int i = 0; i < MAX_AVOIDGOALS; i++ ) {
		if ( gs->avoidgoals[ i ] == number && gs->avoidgoaltimes[ i ] >= AAS_Time() ) {
			return gs->avoidgoaltimes[ i ] - AAS_Time();
		}
	}
	return 0;
}
Esempio n. 18
0
//===========================================================================
//
// Parameter:				-
// Returns:					-
// Changes Globals:		-
//===========================================================================
int BotGetSecondGoal( int goalstate, bot_goal_t *goal ) {
	bot_goalstate_t *gs;

	gs = BotGoalStateFromHandle( goalstate );
	if ( !gs ) {
		return qfalse;
	}
	if ( gs->goalstacktop <= 1 ) {
		return qfalse;
	}
	memcpy( goal, &gs->goalstack[gs->goalstacktop - 1], sizeof( bot_goal_t ) );
	return qtrue;
} //end of the function BotGetSecondGoal
Esempio n. 19
0
static void BotPushGoal( int goalstate, const bot_goal_t* goal, size_t size ) {
	bot_goalstate_t* gs = BotGoalStateFromHandle( goalstate );
	if ( !gs ) {
		return;
	}
	if ( gs->goalstacktop >= MAX_GOALSTACK - 1 ) {
		BotImport_Print( PRT_ERROR, "goal heap overflow\n" );
		BotDumpGoalStack( goalstate );
		return;
	}
	gs->goalstacktop++;
	Com_Memcpy( &gs->goalstack[ gs->goalstacktop ], goal, size );
}
Esempio n. 20
0
//===========================================================================
//
// Parameter:				-
// Returns:					-
// Changes Globals:		-
//===========================================================================
void BotFreeItemWeights( int goalstate ) {
	bot_goalstate_t *gs;

	gs = BotGoalStateFromHandle( goalstate );
	if ( !gs ) {
		return;
	}
	if ( gs->itemweightconfig ) {
		FreeWeightConfig( gs->itemweightconfig );
	}
	if ( gs->itemweightindex ) {
		FreeMemory( gs->itemweightindex );
	}
} //end of the function BotFreeItemWeights
Esempio n. 21
0
void BotDumpAvoidGoals( int goalstate ) {
	bot_goalstate_t* gs = BotGoalStateFromHandle( goalstate );
	if ( !gs ) {
		return;
	}
	for ( int i = 0; i < MAX_AVOIDGOALS; i++ ) {
		if ( gs->avoidgoaltimes[ i ] >= AAS_Time() ) {
			char name[ 32 ];
			BotGoalName( gs->avoidgoals[ i ], name, 32 );
			Log_Write( "avoid goal %s, number %d for %f seconds", name,
				gs->avoidgoals[ i ], gs->avoidgoaltimes[ i ] - AAS_Time() );
		}
	}
}
Esempio n. 22
0
//===========================================================================
//
// Parameter:				-
// Returns:					-
// Changes Globals:		-
//===========================================================================
void BotPushGoal( int goalstate, bot_goal_t *goal ) {
	bot_goalstate_t *gs;

	gs = BotGoalStateFromHandle( goalstate );
	if ( !gs ) {
		return;
	}
	if ( gs->goalstacktop >= MAX_GOALSTACK - 1 ) {
		botimport.Print( PRT_ERROR, "goal heap overflow\n" );
		BotDumpGoalStack( goalstate );
		return;
	} //end if
	gs->goalstacktop++;
	memcpy( &gs->goalstack[gs->goalstacktop], goal, sizeof( bot_goal_t ) );
} //end of the function BotPushGoal
Esempio n. 23
0
//===========================================================================
//
// Parameter:				-
// Returns:					-
// Changes Globals:		-
//===========================================================================
void BotDumpGoalStack( int goalstate ) {
	int i;
	bot_goalstate_t *gs;
	char name[32];

	gs = BotGoalStateFromHandle( goalstate );
	if ( !gs ) {
		return;
	}
	for ( i = 1; i <= gs->goalstacktop; i++ )
	{
		BotGoalName( gs->goalstack[i].number, name, 32 );
		Log_Write( "%d: %s", i, name );
	} //end for
} //end of the function BotDumpGoalStack
Esempio n. 24
0
//===========================================================================
//
// Parameter:				-
// Returns:					-
// Changes Globals:		-
//===========================================================================
float BotAvoidGoalTime( int goalstate, int number ) {
	int i;
	bot_goalstate_t *gs;

	gs = BotGoalStateFromHandle( goalstate );
	if ( !gs ) {
		return 0;
	}
	//don't use the goals the bot wants to avoid
	for ( i = 0; i < MAX_AVOIDGOALS; i++ )
	{
		if ( gs->avoidgoals[i] == number && gs->avoidgoaltimes[i] >= AAS_Time() ) {
			return gs->avoidgoaltimes[i] - AAS_Time();
		} //end if
	} //end for
	return 0;
} //end of the function BotAvoidGoalTime
Esempio n. 25
0
//===========================================================================
//
// Parameter:				-
// Returns:					-
// Changes Globals:		-
//===========================================================================
int BotLoadItemWeights( int goalstate, char *filename ) {
	bot_goalstate_t *gs;

	gs = BotGoalStateFromHandle( goalstate );
	if ( !gs ) {
		return BLERR_CANNOTLOADITEMWEIGHTS;
	}
	//load the weight configuration
	gs->itemweightconfig = ReadWeightConfig( filename );
	if ( !gs->itemweightconfig ) {
		botimport.Print( PRT_FATAL, "couldn't load weights\n" );
		return BLERR_CANNOTLOADITEMWEIGHTS;
	} //end if
	  //if there's no item configuration
	if ( !itemconfig ) {
		return BLERR_CANNOTLOADITEMWEIGHTS;
	}
	//create the item weight index
	gs->itemweightindex = ItemWeightIndex( gs->itemweightconfig, itemconfig );
	//everything went ok
	return BLERR_NOERROR;
} //end of the function BotLoadItemWeights
Esempio n. 26
0
static bool BotChooseNBGItem( int goalstate, const vec3_t origin, const int* inventory, int travelflags,
	const bot_goal_t* ltg, float maxtime ) {
	bot_goalstate_t* gs = BotGoalStateFromHandle( goalstate );
	if ( !gs ) {
		return false;
	}
	if ( !gs->itemweightconfig ) {
		return false;
	}
	//get the area the bot is in
	int areanum = BotReachabilityArea( origin, gs->client );
	//if the bot is in solid or if the area the bot is in has no reachability links
	if ( !areanum || !AAS_AreaReachability( areanum ) ) {
		//use the last valid area the bot was in
		areanum = gs->lastreachabilityarea;
	}
	//remember the last area with reachabilities the bot was in
	gs->lastreachabilityarea = areanum;
	//if still in solid
	if ( !areanum ) {
		return false;
	}

	int ltg_time;
	if ( ltg ) {
		ltg_time = AAS_AreaTravelTimeToGoalArea( areanum, origin, ltg->areanum, travelflags );
	} else {
		ltg_time = 99999;
	}
	//the item configuration
	itemconfig_t* ic = itemconfig;
	if ( !itemconfig ) {
		return false;
	}
	//best weight and item so far
	float bestweight = 0;
	levelitem_t* bestitem = NULL;
	//go through the items in the level
	for ( levelitem_t* li = levelitems; li; li = li->next ) {
		if ( GGameType & GAME_ET ) {
			if ( g_singleplayer ) {
				if ( li->flags & IFL_NOTSINGLE ) {
					continue;
				}
			}
		} else {
			if ( g_gametype == Q3GT_SINGLE_PLAYER ) {
				if ( li->flags & IFL_NOTSINGLE ) {
					continue;
				}
			} else if ( g_gametype >= Q3GT_TEAM ) {
				if ( li->flags & IFL_NOTTEAM ) {
					continue;
				}
			} else {
				if ( li->flags & IFL_NOTFREE ) {
					continue;
				}
			}
		}
		if ( GGameType & GAME_Quake3 && li->flags & IFL_NOTBOT ) {
			continue;
		}
		//if the item is in a possible goal area
		if ( !li->goalareanum ) {
			continue;
		}
		//FIXME: is this a good thing? added this for items that never spawned into the game (f.i. CTF flags in obelisk)
		if ( GGameType & GAME_Quake3 && !li->entitynum && !( li->flags & IFL_ROAM ) ) {
			continue;
		}
		//get the fuzzy weight function for this item
		iteminfo_t* iteminfo = &ic->iteminfo[ li->iteminfo ];
		int weightnum = gs->itemweightindex[ iteminfo->number ];
		if ( weightnum < 0 ) {
			continue;
		}
		//if this goal is in the avoid goals
		if ( !( GGameType & GAME_Quake3 ) && BotAvoidGoalTime( goalstate, li->number ) > 0 ) {
			continue;
		}

		float weight = FuzzyWeightUndecided( inventory, gs->itemweightconfig, weightnum );
		//HACK: to make dropped items more attractive
		if ( li->timeout ) {
			weight += GGameType & GAME_Quake3 ? droppedweight->value : 1000;
		}
		//use weight scale for item_botroam
		if ( GGameType & GAME_Quake3 && li->flags & IFL_ROAM ) {
			weight *= li->weight;
		}

		if ( weight > 0 ) {
			//get the travel time towards the goal area
			int t = AAS_AreaTravelTimeToGoalArea( areanum, origin, li->goalareanum, travelflags );
			//if the goal is reachable
			if ( t > 0 && t < maxtime ) {
				if ( GGameType & GAME_Quake3 ) {
					//if this item won't respawn before we get there
					float avoidtime = BotAvoidGoalTime( goalstate, li->number );
					if ( avoidtime - t * 0.009 > 0 ) {
						continue;
					}
				}

				weight /= ( float )t * TRAVELTIME_SCALE;

				if ( weight > bestweight ) {
					t = 0;
					if ( ltg && !li->timeout ) {
						//get the travel time from the goal to the long term goal
						t = AAS_AreaTravelTimeToGoalArea( li->goalareanum, li->goalorigin, ltg->areanum, travelflags );
					}
					//if the travel back is possible and doesn't take too long
					if ( t <= ltg_time ) {
						bestweight = weight;
						bestitem = li;
					}
				}
			}
		}
	}
	//if no goal item found
	if ( !bestitem ) {
		return false;
	}
	//create a bot goal for this item
	bot_goal_t goal;
	Com_Memset( &goal, 0, sizeof ( bot_goal_t ) );
	iteminfo_t* iteminfo = &ic->iteminfo[ bestitem->iteminfo ];
	VectorCopy( bestitem->goalorigin, goal.origin );
	VectorCopy( iteminfo->mins, goal.mins );
	VectorCopy( iteminfo->maxs, goal.maxs );
	goal.areanum = bestitem->goalareanum;
	goal.entitynum = bestitem->entitynum;
	goal.number = bestitem->number;
	goal.flags = GFL_ITEM;
	if ( GGameType & GAME_Quake3 ) {
		if ( bestitem->timeout ) {
			goal.flags |= GFL_DROPPED;
		}
		if ( bestitem->flags & IFL_ROAM ) {
			goal.flags |= GFL_ROAM;
		}
	}
	goal.iteminfo = bestitem->iteminfo;
	float avoidtime;
	if ( GGameType & GAME_Quake3 ) {
		//if it's a dropped item
		if ( bestitem->timeout ) {
			avoidtime = AVOID_DROPPED_TIME;
		} else {
			avoidtime = iteminfo->respawntime;
			if ( !avoidtime ) {
				avoidtime = AVOID_DEFAULT_TIME;
			}
			if ( avoidtime < AVOID_MINIMUM_TIME ) {
				avoidtime = AVOID_MINIMUM_TIME;
			}
		}
	} else {
		avoidtime = iteminfo->respawntime * 0.5;
		if ( avoidtime < 10 ) {
			avoidtime = AVOID_DEFAULT_TIME;
		}
		//if it's a dropped item
		if ( bestitem->timeout ) {
			avoidtime = AVOID_DROPPED_TIME_WOLF;
		}
	}
	//add the chosen goal to the goals to avoid for a while
	BotAddToAvoidGoals( gs, bestitem->number, avoidtime );
	//push the goal on the stack
	BotPushGoal( goalstate, &goal, sizeof ( goal ) );
	return true;
}
Esempio n. 27
0
//===========================================================================
//
// Parameter:				-
// Returns:					-
// Changes Globals:		-
//===========================================================================
int BotChooseNBGItem( int goalstate, vec3_t origin, int *inventory, int travelflags,
					  bot_goal_t *ltg, float maxtime ) {
	int areanum, t, weightnum, ltg_time;
	float weight, bestweight, avoidtime;
	iteminfo_t *iteminfo;
	itemconfig_t *ic;
	levelitem_t *li, *bestitem;
	bot_goal_t goal;
	bot_goalstate_t *gs;

	gs = BotGoalStateFromHandle( goalstate );
	if ( !gs ) {
		return qfalse;
	}
	if ( !gs->itemweightconfig ) {
		return qfalse;
	}
	//get the area the bot is in
	areanum = BotReachabilityArea( origin, gs->client );
	//if the bot is in solid or if the area the bot is in has no reachability links
	if ( !areanum || !AAS_AreaReachability( areanum ) ) {
		//use the last valid area the bot was in
		areanum = gs->lastreachabilityarea;
	} //end if
	  //remember the last area with reachabilities the bot was in
	gs->lastreachabilityarea = areanum;
	//if still in solid
	if ( !areanum ) {
		return qfalse;
	}
	//
	if ( ltg ) {
		ltg_time = AAS_AreaTravelTimeToGoalArea( areanum, origin, ltg->areanum, travelflags );
	} else { ltg_time = 99999;}
	//the item configuration
	ic = itemconfig;
	if ( !itemconfig ) {
		return qfalse;
	}
	//best weight and item so far
	bestweight = 0;
	bestitem = NULL;
	memset( &goal, 0, sizeof( bot_goal_t ) );
	//go through the items in the level
	for ( li = levelitems; li; li = li->next )
	{
		if ( g_gametype == GT_SINGLE_PLAYER ) {
			if ( li->notsingle ) {
				continue;
			}
		} else if ( g_gametype >= GT_TEAM )     {
			if ( li->notteam ) {
				continue;
			}
		} else {
			if ( li->notfree ) {
				continue;
			}
		}
		//if the item is in a possible goal area
		if ( !li->goalareanum ) {
			continue;
		}
		//get the fuzzy weight function for this item
		iteminfo = &ic->iteminfo[li->iteminfo];
		weightnum = gs->itemweightindex[iteminfo->number];
		if ( weightnum < 0 ) {
			continue;
		}
		//if this goal is in the avoid goals
		if ( BotAvoidGoalTime( goalstate, li->number ) > 0 ) {
			continue;
		}
		//
#ifdef UNDECIDEDFUZZY
		weight = FuzzyWeightUndecided( inventory, gs->itemweightconfig, weightnum );
#else
		weight = FuzzyWeight( inventory, gs->itemweightconfig, weightnum );
#endif //UNDECIDEDFUZZY
#ifdef DROPPEDWEIGHT
		//HACK: to make dropped items more attractive
		if ( li->timeout ) {
			weight += 1000;
		}
#endif //DROPPEDWEIGHT
		if ( weight > 0 ) {
			//get the travel time towards the goal area
			t = AAS_AreaTravelTimeToGoalArea( areanum, origin, li->goalareanum, travelflags );
			//if the goal is reachable
			if ( t > 0 && t < maxtime ) {
				weight /= (float) t * TRAVELTIME_SCALE;
				//
				if ( weight > bestweight ) {
					t = 0;
					if ( ltg && !li->timeout ) {
						//get the travel time from the goal to the long term goal
						t = AAS_AreaTravelTimeToGoalArea( li->goalareanum, li->goalorigin, ltg->areanum, travelflags );
					} //end if
					  //if the travel back is possible and doesn't take too long
					if ( t <= ltg_time ) {
						bestweight = weight;
						bestitem = li;
					} //end if
				} //end if
			} //end if
		} //end if
	} //end for
	  //if no goal item found
	if ( !bestitem ) {
		return qfalse;
	}
	//create a bot goal for this item
	iteminfo = &ic->iteminfo[bestitem->iteminfo];
	VectorCopy( bestitem->goalorigin, goal.origin );
	VectorCopy( iteminfo->mins, goal.mins );
	VectorCopy( iteminfo->maxs, goal.maxs );
	goal.areanum = bestitem->goalareanum;
	goal.entitynum = bestitem->entitynum;
	goal.number = bestitem->number;
	goal.flags = GFL_ITEM;
	goal.iteminfo = bestitem->iteminfo;
	//add the chosen goal to the goals to avoid for a while
	avoidtime = iteminfo->respawntime * 0.5;
	if ( avoidtime < 10 ) {
		avoidtime = AVOID_TIME;
	}
	//if it's a dropped item
	if ( bestitem->timeout ) {
		avoidtime = AVOIDDROPPED_TIME;
	}
	BotAddToAvoidGoals( gs, bestitem->number, avoidtime );
	//push the goal on the stack
	BotPushGoal( goalstate, &goal );
	//
#ifdef DEBUG_AI_GOAL
	if ( bestitem->timeout ) {
		botimport.Print( PRT_MESSAGE, "new nbg dropped item %s\n", ic->iteminfo[bestitem->iteminfo].classname );
	} //end if
	iteminfo = &ic->iteminfo[bestitem->iteminfo];
	botimport.Print( PRT_MESSAGE, "new nbg \"%s\"\n", iteminfo->classname );
#endif //DEBUG_AI_GOAL
	return qtrue;
} //end of the function BotChooseNBGItem