Welcome to the Builder Academy

Question Group Tanks

More
24 May 2020 19:41 - 24 May 2020 19:45 #8727 by cunning
Group Tanks was created by cunning
I have the concept of TANK's who take all the battle damage when groups are in battle and are also the last to enter room and take all the damage from aggressive's. This works great with the old style of Groups w/ Followers.

I always arranged for the groups to enter a room and then ordered them so that the tank was last to enter the room and thus attacked.

In combat, i did auto-assist but i made it very unique, i made it so that auto assist would not only assist the tank, but if the tank was replaced by a new tank in battle, (death of old tank, Tank thrown from battle, some reason the tank was no longer the tank but the next person in line for combat became the tank). Then you would automatically auto assist that new tank.

With new Groups, we have broken this out and I am having some issues. for those do not do not know I have Focused ALS (lou Gherigs) and i am on a new Drug which has some really intense side affects. One of those is it keeps my brain in a fog sometimes. I cannot for the life of me work out the math here. I was hoping if I posted my old code, someone could help me adjust it to the new form of Groups.

I rarely ask for this type of help but since i have been on this new drug, it has and will take some time for me to get used too.

Code:
struct char_data* find_tank(struct char_data* ch) { struct char_data *tch, *next_tch; /* Auto assist - Find out who the tank is in this room - if none, we just keep scanning */ for (tch = world[IN_ROOM(ch)].people; tch; tch = next_tch) { next_tch = tch->next_in_room; /* If the person is not fighting, he is not a tank */ if (!FIGHTING(tch)) continue; /* We are not going to auto assist mobs tanking for us */ if (IS_NPC(tch)) continue; /* If the person is not in group, no need to find a tank for people to auto assist */ if (!AFF_FLAGGED(tch, AFF_GROUP)) continue; /* if person is not in a position to be a tank, skip them. */ if (GET_POS(tch) != POS_FIGHTING) continue; /* if you cannot see them, skip them */ if (!CAN_SEE(tch, ch)) continue; /* Do not want an immortal being the tank */ if (GET_ADMLEVEL(tch) >= ADMLVL_IMMORT) continue; /* now find me the tank */ if (!FIGHTING(FIGHTING(tch))) continue; if (FIGHTING(FIGHTING(tch))) return tch; } return NULL; }
Code:
if (!IS_NPC(ch)) { if ((tank = find_tank(ch)) != NULL) { if (!(master = tank->master)) master = tank; /* now we know the tank and the master, now find the follows and have them auto-assist */ for (k = master->followers; k; k = k->next) { /* skip the person that is tanking for the group */ if (k->follower == tank) continue; if (!CAN_SEE(k->follower, tank)) continue; /* do not want unsuspecting immortals to auto assist */ if (GET_ADMLEVEL(k->follower) >= ADMLVL_IMMORT) continue; /* If we have an NPC follower or if the person is not flagged auto assist, skip them */ if (IS_NPC(k->follower) || !PRF_FLAGGED(k->follower, PRF_AUTOASSIST)) continue; /* Sanity check, if for some odd reason the follower is not in the same room now as the tank, skip them */ if (IN_ROOM(tank) != IN_ROOM(k->follower)) continue; /* if person is not in a position to assist, skip them. */ if (GET_POS(k->follower) != POS_STANDING) continue; /* skip if they are already fighting */ if (FIGHTING(k->follower)) continue; /* Now assist! */ do_assist(k->follower, GET_NAME(tank), 0, 0); k->follower->char_specials.timer = 0; } /* Auto assist the tank with the master of the group - if set for auto assist */ if (!FIGHTING(master) && (master != tank)) { if (PRF_FLAGGED(master, PRF_AUTOASSIST)) if (IN_ROOM(master) == IN_ROOM(tank)) if (GET_POS(master) == POS_STANDING) { do_assist(master, GET_NAME(tank), 0, 0); master->char_specials.timer = 0; } } } } /* End of AutoAssist */ } else stop_fighting(ch);
Code:
void char_from_room(struct char_data *ch) { struct char_data *temp, *i; if (ch == NULL || !VALID_ROOM_RNUM(IN_ROOM(ch))) { log("SYSERR: Extracting char from room NOWHERE. (char_from_room)"); exit(1); } if (GET_EQ(ch, WEAR_LIGHT)) if (GET_OBJ_TYPE(GET_EQ(ch, WEAR_LIGHT)) == ITEM_LIGHT) if (GET_OBJ_VAL(GET_EQ(ch, WEAR_LIGHT), 2)) /* Light is ON */ world[IN_ROOM(ch)].light--; [b] if (ch == world[IN_ROOM(ch)].people) world[IN_ROOM(ch)].people = ch->next_in_room; else { if (world[IN_ROOM(ch)].people) { for (i = world[IN_ROOM(ch)].people; i != NULL && i->next_in_room != ch ; i = i->next_in_room) ; if (i != NULL) { i->next_in_room = ch->next_in_room; } } }[/b] if (FIGHTING(ch)) { if (FIGHTING(FIGHTING(ch)) == ch) stop_fighting(FIGHTING(ch)); stop_fighting(ch); } if (AFF_FLAGGED(ch, AFF_GROUP)) unaffect_group(ch, FALSE); REMOVE_FROM_LIST(ch, world[IN_ROOM(ch)].people, next_in_room); IN_ROOM(ch) = NOWHERE; ch->next_in_room = NULL; }
Last edit: 24 May 2020 19:45 by cunning.
The following user(s) said Thank You: thomas

Please Log in or Create an account to join the conversation.

More
04 Jun 2020 21:12 #8747 by WhiskyTest
Replied by WhiskyTest on topic Group Tanks
Hey cunning, hope you're well!

I thought I'd offer my take on your group tank feature...

I figured why not use the new group structure to have the tanking player be designated by the leader.
When aggressive mobs attack someone there is a "tank check" which would swap out the target if appropriate.
This gets around having to re-order characters entering rooms.

I didn't change anything in perform_violence where auto-assist happens. I felt the tanks function should be separate to auto-assist. (Auto-assist already assists any group member fighting.)

Hopefully this helps as a basis to work from

Designate the tank: group tank <player>
Clear tank: group tank

Attachment grouptank.zip not found

Please Log in or Create an account to join the conversation.

More
05 Jun 2020 16:43 #8751 by cunning
Replied by cunning on topic Group Tanks
Thank you! I just saw this response as it went to my spam folder. I had 60% of that code, so great minds think a like. The real question is how to ensure the tank is always the tank. So aggressive's always hit the tank, in combat the mob hits the tank, if the tank dies the next up is made tank. Hence i had to do the same in perform_violence(). I always ensured the Tank was found, and then hit if the original tank was KIA.

I feel very weird asking for basic stuff, this new med has me scrambled. As a network Design engineer for an ISP now, it has caused me some issues just remembering basic BGP crap that i know inside and out. I forget the little things on this crap.

Please Log in or Create an account to join the conversation.

More
05 Jun 2020 17:48 #8752 by WhiskyTest
Replied by WhiskyTest on topic Group Tanks
No need to feel weird, everyone here has seen the exceptional quality of your contributions!

So our tank is KIA.
As it currently stands the code doesn't assign a new tank. The group leader could do it, which puts the responsibility on them. (interesting gameplay)

Or the code can pick a new tank itself. (convinient)

Would it be smart about it and pick based on highest hitpoints / AC? Or just grab the next group member in the room?

Please Log in or Create an account to join the conversation.

More
05 Jun 2020 22:08 #8757 by cunning
Replied by cunning on topic Group Tanks
Yes, the tank is KIA. The way we do TANKS is that they are always the last in the following group. That way they are the first attacked when the group enters the room. When combat starts, the tank is the one that takes the battle damage. If a Tank dies in battle the next random person is hit, usually the next to last in the follow list. hence my autoassist always looks for the current tank, and assists them.

I also made it so that mob summons, re-animation, all Group upon the cast of the spell. I do this with a new Preference, AUTOGROUP. That way you have the option to auto group the mobile or just have it follow you. I also did group "all". if your not grouped, it creates the group, makes the person who did group all the leader, than groups the rest of the people following. There is another check just in case your grouped already.

Please Log in or Create an account to join the conversation.

More
06 Jun 2020 18:09 #8760 by WhiskyTest
Replied by WhiskyTest on topic Group Tanks
Cool so I've added a couple of functions.

update_tank(ch);
Call this on a character who is currently tanking to automatically find a new tank for their group. It only looks for members in the same room, but you can add your own conditions.
I've added this into die(), so when the tank dies we get a new one automatically.
You might want to add it in other places eg: the tank gets pushed out of the room during combat - call update_tank just before they are pushed.

find_tank(ch, vict);
This returns the tank of vict, if there is one. It also checks if the tank is a valid target for ch, like are they visible.Use this whenever vict is being attacked in such a way that their tank should intervene.
I've added this to the mobile activity for aggro mobs.Hopefully this is getting close to what you are after?

Attachment group_tank.zip not found

Please Log in or Create an account to join the conversation.

Time to create page: 0.228 seconds