The Ballet of the Bots Created 6 years ago2018-12-18 23:10:18 UTC by abbadon abbadon

Created 6 years ago2018-12-18 23:10:18 UTC by abbadon abbadon

Posted 6 years ago2018-12-18 23:10:18 UTC Post #341469
Hello!.
I am writing again to ask you a question about the Bots of my mod.

After modifying things here and there I managed to make the Bots finally begin to be a bit better in terms of combat ability, but I observed something very striking after doing several test sessions from an external point of view.

I have been looking for the cause of the Bots to lower the FPS when they are on screen, I have removed a lot of parts of the navigation code and another parts of the code that was not used at all (jump, stairs, swimming) and I have not had a spectacular success as soon as increase of FPS.

What I have observed is that ALL the Bots of the same team act in coordination, in unison: that is, if a bot shoots an enemy all the bots of the same team shoot the same enemy, if that bot uses the weapon 1 all Bots use Weapon Number 1, and I have observed the same behavior in the four teams of Bots. It is like if when a Bot is created it shares the same AI of the rest of bots created within the same team.

The bot is based on the bot # 10 of Botman.

If you want I can pass the code to those who want to lend a hand.

Thanks in advance.
Posted 5 years ago2018-12-24 13:03:49 UTC Post #341485
And this is the code that "creates" the bot
void CBot::Spawn( )
{
   char c_skill[2];
   char c_index[3];

   CBasePlayer::Spawn();

   pev->flags = FL_CLIENT | FL_FAKECLIENT;

   // set the respawn index value based on key from BotCreate
   strcpy(c_index, GET_INFO_KEY_VALUE(GET_INFOBUFFER(edict( )), "index") );
   sscanf(c_index, "%d", &respawn_index);

   bot_respawn[respawn_index].pBot = (CBasePlayer *)this;

   // get the bot's name and save it in respawn array...
   strcpy(bot_respawn[respawn_index].name, STRING(pev->netname));

   bot_respawn[respawn_index].state = BOT_IDLE;

   pev->ideal_yaw = pev->v_angle.y;
   pev->yaw_speed = BOT_YAW_SPEED;

   // bot starts out in "paused" state since it hasn't moved yet...
   bot_was_paused = TRUE;

   v_prev_origin = pev->origin;
   f_shoot_time = 0;

   fempshot = 0;// Nuevo para la IA del BOT y que use el FEMP

   // get bot's skill level (0=good, 4=bad)
   strcpy(c_skill, GET_INFO_KEY_VALUE(GET_INFOBUFFER(edict( )), "skill") );
   sscanf(c_skill, "%d", &bot_skill);
   bot_skill--;  // make 0 based for array index (now 0-4)
   f_max_speed = 42;

     // pick a wander direction (50% of the time to the left, 50% to the right)
   if (RANDOM_LONG(1, 100) <= 50)
      wander_dir = WANDER_LEFT;
   else
      wander_dir = WANDER_RIGHT;

   f_pause_time = 0;
   f_find_item = 0;

   if (g_pGameRules->IsTeamplay())  // is team play enabled?
   {
      strcpy(model_name, g_pGameRules->GetTeamID(this));

   }
   else
   {
      strcpy(model_name, GET_INFO_KEY_VALUE(GET_INFOBUFFER(edict( )), "model") );
   }


  CBasePlayer *pPlayer = GetClassPtr((CBasePlayer *)pev);//NEW

   bot_model = 0;
   if (strcmp( model_name, "abbadon" ) == 0)
   {
      bot_model = MODEL_ABBADON;

   }
   else if (strcmp( model_name, "manheym") == 0)
   {
      bot_model = MODEL_MANHEYM;

   }
   else if (strcmp( model_name, "blitzkrieg") == 0)
   {
      bot_model = MODEL_BLITZKRIEG;

   }
   else if (strcmp( model_name, "berserk") == 0)
   {
      bot_model = MODEL_BERSERK;

   }

   f_pain_time = gpGlobals->time + 5.0;
   f_weapon_inventory_time = 0;
   f_dont_avoid_wall_time = 0;

   pBotEnemy = NULL;
   pBotUser = NULL;

   switch(RANDOM_LONG(1,4))

   {
    case 1:pPlayer->BotTeam( pPlayer, TEAM1_NAME );pPlayer->m_class = 1;break;//NEW
    case 2:pPlayer->BotTeam( pPlayer, TEAM2_NAME );pPlayer->m_class = 2;break;//NEW
    case 3:pPlayer->BotTeam( pPlayer, TEAM3_NAME );pPlayer->m_class = 3;break;//NEW
    case 4:pPlayer->BotTeam( pPlayer, TEAM4_NAME );pPlayer->m_class = 4;break;//NEW
   }

}
Sorry if I did not posted it before.
Posted 5 years ago2018-12-24 13:17:20 UTC Post #341486
Does Botman's original code produce the same behaviour?
Posted 5 years ago2018-12-24 14:54:01 UTC Post #341487
Well, I cannot say. The bot code was modified to be able to create bots for different teams, and the weaponsĀ“ behaviour, navigation code, and many other things were modified or directly eliminated (my bot is nothing but a moving turret), whatĀ“s true is that every bot acts as its teamĀ“s friends do, no difference in weapon selection or weapon usage or enemy targeting. The only thing they do differently is movement, they walk in different directions and try to reach different battle spots, apart of that, they act as a whole.
Posted 5 years ago2018-12-26 04:32:14 UTC Post #341488
Seems like expected behaviour - the bot AI is just a set of rules the bots follow - the same inputs will probably produce the same outputs so if all the bots see the same enemy and have the same weapon available, they will target the same enemy and use the best weapon based on a set of static rules.
Posted 5 years ago2018-12-28 20:43:15 UTC Post #341506
Oh. I think my bots will act like that forever because I am not able to code a complex combat algorythm. :/

EDIT: Well. I have long thought about what you told me and, after trying and trying variations of the code, the closest thing to what I want to achieve is this:
//=====================================================================
// FEMP
//             30-Nov-2018 1er. Intento de que lo usen los BOTS
//=====================================================================

  if ((pev->weapons & (1<<WEAPON_FEMP)) )
   {
      if (


            ((distance < 100) && (distance > 10 ) && ( fempshot == 0 ))

            && (weapon_choice == 0)

            && (weapon_choice == WEAPON_FEMP)



            || (primary_ammo[WEAPON_TWOHAND]    < 10)


            || ( primary_ammo[WEAPON_SHORYUKEN] < 10 )


            || ( primary_ammo[WEAPON_SIEGE]     < 10 )


            || ( primary_ammo[WEAPON_MJOLNIR]   < 10 )


            || ( primary_ammo[WEAPON_SHREDDER]  < 10 )


        )

    {

        if (primary_ammo[WEAPON_FEMP] > 0) // check if the bot has any ammo left for this weapon...
        {

            if (m_pActiveItem != new_weapon)// check if the bot isn't already using this item...

            SelectItem("weapon_femp");  // select the FEMP

            pev->button |= IN_ATTACK;  // use primary attack (bang! bang!)

            f_shoot_time = gpGlobals->time + 10.0 + RANDOM_FLOAT(primary_fire_delay[WEAPON_FEMP][bot_skill][0],primary_fire_delay[WEAPON_FEMP][bot_skill][1]);     // set next time to shoot

            fempshot +=1; // Damos un fempshot para limitar su uso

            return TRUE;

            if ( ( pev->health <= 100 ) )

                {
                    pev->button |= IN_ATTACK2;

                } // Posicion original del codigo del AUTO-HEALTH

            if  ( f_shoot_time = gpGlobals->time = 15.0 )

                {
                    fempshot -=1;
                }
        }
      }
    }
  return FALSE;


}
And this:
//=============================================================================================
// WEAPON URAKEN/CROWBAR I cannot make the bot use this weapon!!! I suck in coding...4-May-2015
// GOT IT!! 24-November-2018 but with Issues...
//=============================================================================================

if (pev->weapons & (1<<WEAPON_CROWBAR))

  {
      if (

             (distance == 0)

          && (weapon_choice == 0)

          || (( fempshot == 1) && ( f_shoot_time = gpGlobals->time ==   0.0 ))


          && (weapon_choice == WEAPON_CROWBAR)




          || ( primary_ammo[WEAPON_TWOHAND]   ==0 )

          || ( primary_ammo[WEAPON_SHORYUKEN] ==0 )

          || ( primary_ammo[WEAPON_SIEGE]     ==0 )

          || ( primary_ammo[WEAPON_MJOLNIR]   ==0 )

          || ( primary_ammo[WEAPON_SHREDDER]  ==0 )

          )
    {

          new_weapon = weapon_ptr[WEAPON_CROWBAR];

         {

            if (m_pActiveItem != new_weapon)// check if the bot isn't already using this item...

            SelectItem("weapon_crowbar");  // select the crowbar

            pev->button |= IN_ATTACK;      // use primary attack (whack! whack!)

            f_shoot_time = gpGlobals->time + 4.0 + RANDOM_FLOAT(primary_fire_delay[WEAPON_CROWBAR][bot_skill][0],primary_fire_delay[WEAPON_CROWBAR][bot_skill][1]);

            return TRUE;

         }


    }



   }
//========================================================================================
Well. What I obtained is that the Bots now "seem" to act differently: some of them use one weapon and others use a different weapon, but, if one or two of them are slightly close to each ohter, they tend to use the same weapon. For them to use a diferent weapon the distance must be much bigger i.e: one in the outer circle and the ohter in the third farthest of the bridges. :\

What I want is the Bots use the Uraken when the enemy is very close, and the FEMP if the distance is farther, BUT, keeping them from sticking to that weapon, because, once they start to use one or another, they seem to like it so much and hardly choose another weapon... :quizzical:

Also, they seem to not detect very well the distances, because they use short range weapons when thereĀ“s no close enemy.

Also. I have one more doubt and probably the dumbest, but... how can I measure distances in the map editor?. I mean, I want the Bot to use weapon X if distance is Y, but I donĀ“t know how to measure it (remember that I use a block the size of the info_player_start to do calculations!!). :walter:

Thanks in anticipation, :crowbar:
Posted 5 years ago2018-12-30 19:44:04 UTC Post #341524
I don't think you can measure distance in QuArK directly. I've used it for some time, but I never found a way. Unless you turn on the grid. I remember yours was turned off.

See those green-ish dots? (might not be visible so see full image)See those green-ish dots? (might not be visible so see full image)

The option is right here:
User posted image
Each square on the grid is aƗa units, and a is whatever your grid size is set to.

As for the bots, I'd go with a personality approach (something like int m_iPersonality, or even better, an enum) and each bot gets a random personality at spawn. And then depending on their personality, they can fire slower, faster, and even prefer weapons.
Admer456 Admer456If it ain't broken, don't fox it!
Posted 5 years ago2018-12-30 22:42:48 UTC Post #341525
Hi Admer!!, yes, I have added that is in the shape of a skill method. But I am thinking now in adding a find entities method for the weapon itself. :)
Thanks for the grid hint!!, I did never use it, ha ha!!, what a moron!!! ;)
Posted 5 years ago2019-01-03 03:42:05 UTC Post #341538
As for the bots, I'd go with a personality approach (something like int m_iPersonality, or even better, an enum) and each bot gets a random personality at spawn. And then depending on their personality, they can fire slower, faster, and even prefer weapons.
Agree.
Posted 5 years ago2019-01-04 22:01:19 UTC Post #341543
Sounds complicated... :roll: IĀ“ll take a look to HPBot Template #4 to see how it manages bot spawning and connects to the CS and other ModĀ“s gameplay. :crowbar:

One question: Where should I put this code in the Crowbar.cpp to make so if you swing or hit X times with the crowbar it gives you ammo?
count++;
if(count>=6)
{
  m_pPlayer->m_rgAmmo[m_iPrimaryAmmoType]+=25;//Erase if it works!!

  if (FBitSet(m_pPlayer->pev->flags, FL_FAKECLIENT)){m_pPlayer->m_rgAmmo[m_iPrimaryAmmoType]+=101;}// For Bots Only

     m_flNextPrimaryAttack = UTIL_WeaponTimeBase() + 0.4;

     count=0;// Reset Counter
}
Of course int count is already declared in crowbar code in weapons.h

I put it in int CCrowbar::Swing( int fFirst ) right after TraceResult tr; but with no luck... :(

Because I cannot make the Bots quit using the crowbar after depleting their ammo, I thought that I will let them use the crowbar for a while and then give them some ammo to fight again, use the RELOAD call, etc. :crowbar:
Posted 5 years ago2019-01-04 23:38:43 UTC Post #341546
Seems like an okay place for it but if it's not working probably add some logging to see what's going on.
Posted 5 years ago2019-01-05 15:39:32 UTC Post #341552
Well, put me the label of "moron" again. I am asking to the code to add PRIMARY AMMO to a weapon that HAS NO PRIMARY AMMO to load in...

I have to add better a pPlayer there and AddAmmo to the player with the ( number, ammo type, number) part (As in the monster_trolley) :crowbar:

I will test it and post the results. ;)
Posted 5 years ago2019-01-05 18:19:35 UTC Post #341556
I am asking to the code to add PRIMARY AMMO to a weapon that HAS NO PRIMARY AMMO to load in...
Oh, the joys of coding. :D
Admer456 Admer456If it ain't broken, don't fox it!
Posted 5 years ago2019-01-05 19:32:45 UTC Post #341558
Ha ha!!, yes, itĀ“s a pain in the ass when you have no idea of what you are doing!!, is like "hey!, what if I mix water with solid sodium?", "funny" things will happen... :crowbar: :walter:

Aniway, the code works now. I am now doing the logic part of the code so the Bot changes from FEMP to CROWBAR to MACHINE GUNS... :freeman:

Well, now all works like a charm. Bots "seem" to work as real players, they use the FEMP, the Uraken... now I am working with the FEMP effect, I have used this code:
// Particle Burst

                MESSAGE_BEGIN( MSG_BROADCAST, SVC_TEMPENTITY );
                WRITE_BYTE( TE_TELEPORT );
                WRITE_COORD(pev->origin.x);
                WRITE_COORD(pev->origin.y);
                WRITE_COORD(pev->origin.z);
                WRITE_BYTE( 0 );
                WRITE_BYTE( 0 );
                WRITE_BYTE( 3 ); // life
                WRITE_BYTE( 24);  // width
                WRITE_BYTE( 5 );   // noise
                MESSAGE_END(  );
I want it to be BIGGER, yes it plays, but is small, I want it to reach a farther distance. I have tried different values for life, width, and noise, but it accelerates the shockwaves, the burst remain the same. Any ideas? :\
Posted 5 years ago2019-01-08 04:39:22 UTC Post #341584
const.h says TE_TELEPORT only takes three coord arguments - maybe use another SVC message type that has a width parameter.
Posted 5 years ago2019-01-08 15:31:54 UTC Post #341590
Mmmm, as far as I can see, TE_ entities show not many options to customize... TE_BEAMTORUS create a nice effect, but itĀ“s a 2D planar effect. The TE_LARGEFUNNEL shows almost what I want, but is narrow and in a greenish color... :/ Well, it is not a must, I just want to add a little more detail to the final effects of the MOD. :D Aniway, could I add more optios or is it hardcoded in the engine so I cannot add width, life, etc to its parameters?
Posted 5 years ago2019-01-09 04:37:26 UTC Post #341597
All the TE_ effects are hard-coded in the engine.
Posted 5 years ago2019-01-09 14:39:17 UTC Post #341603
F... damn!! :( Well, the TE_TELEPORT effect is right by now, unless I learn enough C++ to make the effect I want on my own, which is ... impossible. Thanks a lot for your help! :P

BTW: how can I disable dev messages?, I have no command line added to the shortcut but they still appear flooding the console.
Posted 5 years ago2019-01-10 04:54:51 UTC Post #341609
What is the message?
Posted 5 years ago2019-01-10 14:57:49 UTC Post #341615
Well, lots of them:

script "Anim4" can't find monster "apua"
Found apub, but can't play!
Found ascari, but can't play!
Found crane, but can't play!

Many of those as an example....continuously. I donĀ“t want any messages apart form the ones sent by the game itself like "reload" or "x has killed y". :/
Posted 5 years ago2019-01-11 06:13:49 UTC Post #341616
Not sure what's outputting them but maybe they're unsuppressible errors? Maybe the engine will always warn you regardless of what developer is set to.
Posted 5 years ago2019-01-11 18:15:48 UTC Post #341618
I am afraid YES. They donĀ“t disappear... :(
Posted 5 years ago2019-01-11 21:10:08 UTC Post #341620
Probably wouldn't be too hard to fix whatever is causing the issues - looks like missing animations or something like that.
Posted 5 years ago2019-01-11 21:26:15 UTC Post #341622
I have tried everything I know. In fact, I have decompiled-compiled the models to see if something is not rightly placed, but HLMV shows no problem (ACT_ thingy included) and the extrange thing is that all animations are present, and the npcs act as they should. Probably is something related with Xash. :/
Posted 5 years ago2019-01-12 10:52:21 UTC Post #341625
The can't find monster looks like a missing entity: https://github.com/ValveSoftware/halflife/blob/master/dlls/scripted.cpp#L486
You'll have to do some searching to figure out what the other one is.
Posted 5 years ago2019-01-13 11:05:27 UTC Post #341628
I have checked it, it is something related with Xash, iĀ“m afraid. All is ok, but it keeps telling me that there are problems. Funny and bothering at the same time. :\
You must be logged in to post a response.