/* ============== BotAIShutdownClient ============== */ int BotAIShutdownClient( int client ) { bot_state_t *bs; // Wolfenstein if ( g_entities[client].r.svFlags & SVF_CASTAI ) { AICast_ShutdownClient( client ); return BLERR_NOERROR; } // done. bs = botstates[client]; if ( !bs || !bs->inuse ) { // BotAI_Print(PRT_ERROR, "client %d already shutdown\n", client); return BLERR_AICLIENTALREADYSHUTDOWN; } if ( BotChat_ExitGame( bs ) ) { trap_BotEnterChat( bs->cs, bs->client, CHAT_ALL ); } trap_BotFreeMoveState( bs->ms ); //free the goal state trap_BotFreeGoalState( bs->gs ); //free the chat file trap_BotFreeChatState( bs->cs ); //free the weapon weights trap_BotFreeWeaponState( bs->ws ); //free the bot character trap_BotFreeCharacter( bs->character ); // BotFreeWaypoints( bs->checkpoints ); BotFreeWaypoints( bs->patrolpoints ); //clear the bot state memset( bs, 0, sizeof( bot_state_t ) ); //set the inuse flag to qfalse bs->inuse = qfalse; //there's one bot less numbots--; //everything went ok return BLERR_NOERROR; }
/* ============== BotAIShutdownClient ============== */ int BotAIShutdownClient(int client, qboolean restart) { bot_state_t *bs; bs = botstates[client]; if (!bs || !bs->inuse) { //BotAI_Print(PRT_ERROR, "BotAIShutdownClient: client %d already shutdown\n", client); return qfalse; } if (restart) { BotWriteSessionData(bs); } if (BotChat_ExitGame(bs)) { trap_BotEnterChat(bs->cs, bs->client, CHAT_ALL); } trap_BotFreeMoveState(bs->ms); //free the goal state trap_BotFreeGoalState(bs->gs); //free the chat file trap_BotFreeChatState(bs->cs); //free the weapon weights trap_BotFreeWeaponState(bs->ws); //free the bot character trap_BotFreeCharacter(bs->character); // BotFreeWaypoints(bs->checkpoints); BotFreeWaypoints(bs->patrolpoints); //clear activate goal stack BotClearActivateGoalStack(bs); //clear the bot state memset(bs, 0, sizeof(bot_state_t)); //set the inuse flag to qfalse bs->inuse = qfalse; //there's one bot less numbots--; //everything went ok return qtrue; }
/* ============== BotAISetupClient ============== */ int BotAISetupClient( int client, struct bot_settings_s *settings ) { char filename[MAX_PATH], name[MAX_PATH], gender[MAX_PATH]; bot_state_t *bs; int errnum; if ( !botstates[client] ) { botstates[client] = G_Alloc( sizeof( bot_state_t ) ); } bs = botstates[client]; if ( bs && bs->inuse ) { BotAI_Print( PRT_FATAL, "client %d already setup\n", client ); return qfalse; } if ( !trap_AAS_Initialized() ) { BotAI_Print( PRT_FATAL, "AAS not initialized\n" ); return qfalse; } //load the bot character bs->character = trap_BotLoadCharacter( settings->characterfile, settings->skill ); if ( !bs->character ) { BotAI_Print( PRT_FATAL, "couldn't load skill %f from %s\n", settings->skill, settings->characterfile ); return qfalse; } //copy the settings memcpy( &bs->settings, settings, sizeof( bot_settings_t ) ); //allocate a goal state bs->gs = trap_BotAllocGoalState( client ); //load the item weights trap_Characteristic_String( bs->character, CHARACTERISTIC_ITEMWEIGHTS, filename, MAX_PATH ); errnum = trap_BotLoadItemWeights( bs->gs, filename ); if ( errnum != BLERR_NOERROR ) { trap_BotFreeGoalState( bs->gs ); return qfalse; } //allocate a weapon state bs->ws = trap_BotAllocWeaponState(); //load the weapon weights trap_Characteristic_String( bs->character, CHARACTERISTIC_WEAPONWEIGHTS, filename, MAX_PATH ); errnum = trap_BotLoadWeaponWeights( bs->ws, filename ); if ( errnum != BLERR_NOERROR ) { trap_BotFreeGoalState( bs->gs ); trap_BotFreeWeaponState( bs->ws ); return qfalse; } //allocate a chat state bs->cs = trap_BotAllocChatState(); //load the chat file trap_Characteristic_String( bs->character, CHARACTERISTIC_CHAT_FILE, filename, MAX_PATH ); trap_Characteristic_String( bs->character, CHARACTERISTIC_CHAT_NAME, name, MAX_PATH ); errnum = trap_BotLoadChatFile( bs->cs, filename, name ); if ( errnum != BLERR_NOERROR ) { trap_BotFreeChatState( bs->cs ); trap_BotFreeGoalState( bs->gs ); trap_BotFreeWeaponState( bs->ws ); return qfalse; } //get the gender characteristic trap_Characteristic_String( bs->character, CHARACTERISTIC_GENDER, gender, MAX_PATH ); //set the chat gender if ( *gender == 'f' || *gender == 'F' ) { trap_BotSetChatGender( bs->cs, CHAT_GENDERFEMALE ); } else if ( *gender == 'm' || *gender == 'M' ) { trap_BotSetChatGender( bs->cs, CHAT_GENDERMALE ); } else { trap_BotSetChatGender( bs->cs, CHAT_GENDERLESS );} bs->inuse = qtrue; bs->client = client; bs->entitynum = client; bs->setupcount = 4; bs->entergame_time = trap_AAS_Time(); bs->ms = trap_BotAllocMoveState(); bs->walker = trap_Characteristic_BFloat( bs->character, CHARACTERISTIC_WALKER, 0, 1 ); numbots++; if ( trap_Cvar_VariableIntegerValue( "bot_testichat" ) ) { trap_BotLibVarSet( "bot_testichat", "1" ); BotChatTest( bs ); } //NOTE: reschedule the bot thinking BotScheduleBotThink(); // return qtrue; }
/* * BotAISetupClient */ int BotAISetupClient(int client, struct bot_settings_s *settings, qbool restart) { char filename[MAX_PATH], name[MAX_PATH], gender[MAX_PATH]; bot_state_t *bs; int errnum; if(!botstates[client]) botstates[client] = G_Alloc(sizeof(bot_state_t)); bs = botstates[client]; if(bs && bs->inuse){ BotAI_Print(PRT_FATAL, "BotAISetupClient: client %d already setup\n", client); return qfalse; } if(!trap_AAS_Initialized()){ BotAI_Print(PRT_FATAL, "AAS not initialized\n"); return qfalse; } /* load the bot character */ bs->character = trap_BotLoadCharacter(settings->characterfile, settings->skill); if(!bs->character){ BotAI_Print(PRT_FATAL, "couldn't load skill %f from %s\n", settings->skill, settings->characterfile); return qfalse; } /* copy the settings */ memcpy(&bs->settings, settings, sizeof(bot_settings_t)); /* allocate a goal state */ bs->gs = trap_BotAllocGoalState(client); /* load the item weights */ trap_Characteristic_String(bs->character, CHARACTERISTIC_ITEMWEIGHTS, filename, MAX_PATH); errnum = trap_BotLoadItemWeights(bs->gs, filename); if(errnum != BLERR_NOERROR){ trap_BotFreeGoalState(bs->gs); return qfalse; } /* allocate a weapon state */ bs->ws = trap_BotAllocWeaponState(); /* load the weapon weights */ trap_Characteristic_String(bs->character, CHARACTERISTIC_WEAPONWEIGHTS, filename, MAX_PATH); errnum = trap_BotLoadWeaponWeights(bs->ws, filename); if(errnum != BLERR_NOERROR){ trap_BotFreeGoalState(bs->gs); trap_BotFreeWeaponState(bs->ws); return qfalse; } /* allocate a chat state */ bs->cs = trap_BotAllocChatState(); /* load the chat file */ trap_Characteristic_String(bs->character, CHARACTERISTIC_CHAT_FILE, filename, MAX_PATH); trap_Characteristic_String(bs->character, CHARACTERISTIC_CHAT_NAME, name, MAX_PATH); errnum = trap_BotLoadChatFile(bs->cs, filename, name); if(errnum != BLERR_NOERROR){ trap_BotFreeChatState(bs->cs); trap_BotFreeGoalState(bs->gs); trap_BotFreeWeaponState(bs->ws); return qfalse; } /* get the gender characteristic */ trap_Characteristic_String(bs->character, CHARACTERISTIC_GENDER, gender, MAX_PATH); /* set the chat gender */ if(*gender == 'f' || *gender == 'F') trap_BotSetChatGender( bs->cs, CHAT_GENDERFEMALE); else if(*gender == 'm' || *gender == 'M') trap_BotSetChatGender( bs->cs, CHAT_GENDERMALE); else trap_BotSetChatGender(bs->cs, CHAT_GENDERLESS); bs->inuse = qtrue; bs->client = client; bs->entitynum = client; bs->setupcount = 4; bs->entergame_time = FloatTime(); bs->ms = trap_BotAllocMoveState(); bs->walker = trap_Characteristic_BFloat(bs->character, CHARACTERISTIC_WALKER, 0, 1); numbots++; if(trap_cvargeti("bot_testichat")){ trap_BotLibVarSet("bot_testichat", "1"); BotChatTest(bs); } /* NOTE: reschedule the bot thinking */ BotScheduleBotThink(); /* if interbreeding start with a mutation */ if(bot_interbreed) trap_BotMutateGoalFuzzyLogic(bs->gs, 1); /* if we kept the bot client */ if(restart) BotReadSessionData(bs); /* bot has been setup succesfully */ return qtrue; }