Well, it took a long time (as you might imagine, balancing this thing was a real pain in the ass), but it's done. You can download it along with the other mods here. And, no, this one also isn't compatible with UP or RP, though that'll probably be fixed soon.
Anyway, before I get into what it is exactly that the mod does, here's why I did it:
(1) Variation: Too many groups in Fallout look like they have a standard issue firearm. Not only doesn't it make a lot of sense in a post-apoc setting that every mexican mobster has a 10MM SMG, but it also neglects a lot of interesting animations (pistols, rifles, etc.).
(2) Replayability (obviously): you can by now already dream the progression in which you'll acquire your weapons, and which weapons will be utterly useless by the time you get them (Mauser, Grease Gun, Switchblade, etc.). It's nice to have that switched up a bit.
(3) Ye Olde Ammo Problem: There's just way too much ammo in Fallout for a post-apoc setting. I'll get to how I try to address this in a minute, but you'll see that for this whole mod I've tried to incorporate part of the following comment by VD over at the Codex:
I disagree with a lot of things he's saying (from a gameplay standpoint), but that last thing is what makes most sense to me and that I've tried to generalize across the game: expect to see way more critters with a half-loaded rifle and a quarter-loaded pistol on the side.
To explain what the mod does I'll use segments of the script as an examples in spoiler tags:
First, I reduce the ammo stack sizes to about a fifth of their original size (some exceptions are: 45 cal and 9mm, which get reduced by less). I have no clue why the devs made such huge ammo stacks (50 .223 rounds, really?) other than to make sense of the weight system, but it's just way out of hand for the setting.
[spoiler:3c4f006f02]
[/spoiler:3c4f006f02]
Next, I check that it's the first time a map is run, and if that is the case, each critter on the map gets checked if he's one of the character models which will get randomized (generally, "combat" humans (so no peasants), ghouls and super mutants), and whether it's not one of the exceptions (so, if it's not the player, a party member, or critters like the Salvatore men, Lo Pan, etc. which shouldn't be randomized for obvious reasons, though I probably missed some).
[spoiler:3c4f006f02]
[/spoiler:3c4f006f02]
Next, each inventory slot on the critter gets checked for weapons and ammo, and those get removed.
[spoiler:3c4f006f02]
[/spoiler:3c4f006f02]
After that, I make a list of all the compatible animations, so Super Mutants can't get knives, etc. (I'll probably update this after the final RP/UP release).
[spoiler:3c4f006f02]
[/spoiler:3c4f006f02]
Then comes the most important part: establishing who gets what class of weapon. I do so on the basis of how high tech the area is, combined with the critter's experience value.
[spoiler:3c4f006f02]
[/spoiler:3c4f006f02]
Then, if the critter is not a melee/unarmed character, the roll is made for his ranged weapon. I simply made a list of the ranged weapons from "bad" to "good", but let me know if you think the order should be different.
[spoiler:3c4f006f02]
[/spoiler:3c4f006f02]
Then the ammo type gets randomized if there are multiple possibilities (e.g. 10MM AP/JHP)
[spoiler:3c4f006f02]
[/spoiler:3c4f006f02]
Next, the ammount of ammo gets determined, based on the same factors as for the weapon itself. The possible outcome ranges from the weapon having a 1/4 filled magazine to a maximum of five additional ammo stacks (so that'd probably only be one extra magazine in the old system).
[spoiler:3c4f006f02]
[/spoiler:3c4f006f02]
Next, the ranged critter gets a possible (weaker) roll for an additional sidearm, whose ammo count is always 1/2 to 3/4 empty.
[spoiler:3c4f006f02]
[/spoiler:3c4f006f02]
Next, the melee character get a roll; first the bruisers (clubs, sledges, brass knuckles, etc.), then the agile fighters (knives and spears). Energy melee weapons get an ammo roll.
[spoiler:3c4f006f02]
[/spoiler:3c4f006f02]
Next, both ranged and melee characters get a possible (1/5 or so chance, and only if they have at least some throwing skill) roll for a throwing weapons. With throwing knives there'll be more chance of getting additional ones than with grenades and such.
[spoiler:3c4f006f02]
[/spoiler:3c4f006f02]
Finally, both character types get a possible (weaker) roll for a (additional, in the case of melee characters) melee weapon.
[spoiler:3c4f006f02]
[/spoiler:3c4f006f02]
Note that all critters immediately wield their primary weapon, so you sometimes get a bit strange scene upon first entering a map of characters holstering their destroyed weapons and unholstering their new ones, but nothing too bad.
Anyway, before I get into what it is exactly that the mod does, here's why I did it:
(1) Variation: Too many groups in Fallout look like they have a standard issue firearm. Not only doesn't it make a lot of sense in a post-apoc setting that every mexican mobster has a 10MM SMG, but it also neglects a lot of interesting animations (pistols, rifles, etc.).
(2) Replayability (obviously): you can by now already dream the progression in which you'll acquire your weapons, and which weapons will be utterly useless by the time you get them (Mauser, Grease Gun, Switchblade, etc.). It's nice to have that switched up a bit.
(3) Ye Olde Ammo Problem: There's just way too much ammo in Fallout for a post-apoc setting. I'll get to how I try to address this in a minute, but you'll see that for this whole mod I've tried to incorporate part of the following comment by VD over at the Codex:
You didn't really have to survive in Fallout (which deserves a special topic), but what bugged me the most was the overabundance of ammo.
So, if I was designing a Fallout-like game, I'd make melee a pretty much mandatory skill, as melee weapons are the easiest to make, find, and use. I'd make widely available guns clearly superior to melee but unreliable (high chance of misfire due to wear, tear, and poor maintenance). 30-40% chance of misfire maybe.
Then you'd have rare "mothballed" guns in mint condition and special weapons, found in pre-war facilities, sort of like +2 weapons in fantasy dungeons. Ammo is rare, so running out should be a frequent occasion. Ammo for special weapons should be extremely rare. Burst mode should be the last resort option.
In the end, a well to-do post-apoc warrior would have a mint condition magnum with 2 rounds, an old glock with 12 rounds, a well maintained hunting rifle with 5 rounds, and an assortment of melee weapons.
I disagree with a lot of things he's saying (from a gameplay standpoint), but that last thing is what makes most sense to me and that I've tried to generalize across the game: expect to see way more critters with a half-loaded rifle and a quarter-loaded pistol on the side.
To explain what the mod does I'll use segments of the script as an examples in spoiler tags:
First, I reduce the ammo stack sizes to about a fifth of their original size (some exceptions are: 45 cal and 9mm, which get reduced by less). I have no clue why the devs made such huge ammo stacks (50 .223 rounds, really?) other than to make sense of the weight system, but it's just way out of hand for the setting.
[spoiler:3c4f006f02]
Code:
if get_proto_data(PID_10MM_AP, 40) != 5 then begin
set_proto_data(PID_10MM_AP, 40, 5);
end if get_proto_data(PID_10MM_JHP, 40) != 5 then begin
set_proto_data(PID_10MM_JHP, 40, 5);
end if get_proto_data(PID_5MM_JHP, 40) != 10 then begin
set_proto_data(PID_5MM_JHP, 40, 10);
end if get_proto_data(PID_5MM_AP, 40) != 10 then begin
set_proto_data(PID_5MM_AP, 40, 10);
end if get_proto_data(PID_44_MAGNUM_JHP, 40) != 4 then begin
set_proto_data(PID_44_MAGNUM_JHP, 40, 4);
end if get_proto_data(PID_44_FMJ_MAGNUM, 40) != 4 then begin
set_proto_data(PID_44_FMJ_MAGNUM, 40, 4);
end if get_proto_data(PID_223_FMJ, 40) != 10 then begin
set_proto_data(PID_223_FMJ, 40, 10);
end if get_proto_data(PID_45_CALIBER_AMMO, 40) != 5 then begin
set_proto_data(PID_45_CALIBER_AMMO, 40, 5);
end if get_proto_data(PID_2MM_EC_AMMO, 40) != 10 then begin
set_proto_data(PID_2MM_EC_AMMO, 40, 10);
end if get_proto_data(PID_4_7MM_CASELESS, 40) != 10 then begin
set_proto_data(PID_4_7MM_CASELESS, 40, 10);
end if get_proto_data(PID_7_62MM_AMMO, 40) != 10 then begin
set_proto_data(PID_7_62MM_AMMO, 40, 10);
end if get_proto_data(PID_9MM_AMMO, 40) != 5 then begin
set_proto_data(PID_9MM_AMMO, 40, 5);
end if get_proto_data(PID_9MM_BALL, 40) != 5 then begin
set_proto_data(PID_9MM_BALL, 40, 5);
end if get_proto_data(PID_14MM_AP, 40) != 6 then begin
set_proto_data(PID_14MM_AP, 40, 6);
end if get_proto_data(PID_SHOTGUN_SHELLS, 40) != 4 then begin
set_proto_data(PID_SHOTGUN_SHELLS, 40, 4);
end if get_proto_data(PID_FLAMETHROWER_FUEL, 40) != 5 then begin
set_proto_data(PID_FLAMETHROWER_FUEL, 40, 5);
end if get_proto_data(PID_FLAMETHROWER_FUEL_MK_II, 40) != 5 then begin
set_proto_data(PID_FLAMETHROWER_FUEL_MK_II, 40, 5);
end if get_proto_data(PID_HN_AP_NEEDLER_CARTRIDGE, 40) != 6 then begin
set_proto_data(PID_HN_AP_NEEDLER_CARTRIDGE, 40, 6);
end if get_proto_data(PID_HN_NEEDLER_CARTRIDGE, 40) != 6 then begin
set_proto_data(PID_HN_NEEDLER_CARTRIDGE, 40, 6);
end if get_proto_data(PID_MICRO_FUSION_CELL, 40) != 10 then begin
set_proto_data(PID_MICRO_FUSION_CELL, 40, 10);
end if get_proto_data(PID_SMALL_ENERGY_CELL, 40) != 8 then begin
set_proto_data(PID_SMALL_ENERGY_CELL, 40, 8);
end
Next, I check that it's the first time a map is run, and if that is the case, each critter on the map gets checked if he's one of the character models which will get randomized (generally, "combat" humans (so no peasants), ghouls and super mutants), and whether it's not one of the exceptions (so, if it's not the player, a party member, or critters like the Salvatore men, Lo Pan, etc. which shouldn't be randomized for obvious reasons, though I probably missed some).
[spoiler:3c4f006f02]
Code:
foreach rndcritter in list_as_array(LIST_CRITTERS) begin
//display_msg("critter");
if ((proto_data(obj_pid(rndcritter),cr_fid) == FID_NMMAXX) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_NFMAXX) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_HMBMET) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_NFMETL) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_NMCOPP) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_NAVGUL) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_NAGHUL) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_NMMEXI) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_NMLTHR) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_NMGANG) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_NMRGNG) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_MAMTNT) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_MAMTN2) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_NAPOWR) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_HMMAXX) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_HFMAXX) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_HMMETL) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_HFMETL) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_HMLTHR) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_HFLTHR) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_HMCMBT) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_HFCMBT) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_HAPOWR) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_HANPWR)) and rndcritter!=dude_obj and obj_pid(rndcritter) != PID_LIL_JESUS and obj_pid(rndcritter) != PID_LOPAN and obj_pid(rndcritter) != PID_THE_DRAGON and obj_pid(rndcritter) != PID_SALVATORE_THUG_1 and obj_pid(rndcritter) != PID_SALVATORE_THUG_2 and obj_pid(rndcritter) != PID_MASON and obj_pid(rndcritter) != PID_GUN_MERCHANT and not (party_member_obj(obj_pid(rndcritter))) then begin
Next, each inventory slot on the critter gets checked for weapons and ammo, and those get removed.
[spoiler:3c4f006f02]
Code:
if (inven_count(rndcritter) > 2) and ((obj_item_subtype(inven_ptr(rndcritter, 2)) == item_type_weapon) or (obj_item_subtype(inven_ptr(rndcritter, 2)) == item_type_ammo)) then begin
item:=(inven_ptr(rndcritter, 2));
destroy_object(inven_ptr(rndcritter, 2));
if (inven_ptr(rndcritter, 2) == item) then begin
destroy_object(item);
if (inven_ptr(rndcritter, 2) == item) then begin
destroy_object(item);
if (inven_ptr(rndcritter, 2) == item) then begin
destroy_object(item);
if (inven_ptr(rndcritter, 2) == item) then begin
destroy_object(item);
if (inven_ptr(rndcritter, 2) == item) then begin
destroy_object(item);
if (inven_ptr(rndcritter, 2) == item) then begin
destroy_object(item);
if (inven_ptr(rndcritter, 2) == item) then begin
destroy_object(item);
end
end
end
end
end
end
end
end
After that, I make a list of all the compatible animations, so Super Mutants can't get knives, etc. (I'll probably update this after the final RP/UP release).
[spoiler:3c4f006f02]
Code:
rifle:=((proto_data(obj_pid(rndcritter),cr_fid) != FID_NMMAXX) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NFMAXX) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_HMBMET) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NFMETL) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NAPOWR) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NAVGUL) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_MAMTNT) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_MAMTN2));
pistol:=((proto_data(obj_pid(rndcritter),cr_fid) != FID_NFMAXX) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NFMETL) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NAPOWR) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NAGHUL) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_MAMTNT) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_MAMTN2));
smg:=((proto_data(obj_pid(rndcritter),cr_fid) != FID_NMMAXX) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMLTHR) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_HMBMET) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NFMETL) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NAPOWR) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NAGHUL) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_MAMTNT) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_MAMTN2));
big_gun:=((proto_data(obj_pid(rndcritter),cr_fid) != FID_NMMAXX) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NFMAXX) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_HMBMET) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NFMETL) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NAPOWR) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NAVGUL) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NAGHUL) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMMEXI) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMLTHR));
minigun:=((proto_data(obj_pid(rndcritter),cr_fid) != FID_NMMAXX) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NFMAXX) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_HMBMET) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NFMETL) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMCOPP) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NAVGUL) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NAGHUL) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMMEXI) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMLTHR) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMGANG) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMRGNG));
rocket_launcher:=((proto_data(obj_pid(rndcritter),cr_fid) != FID_NMMAXX) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NFMAXX) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_HMBMET) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NFMETL) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMCOPP) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NAVGUL) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NAGHUL) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMMEXI) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMLTHR) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMGANG) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMRGNG));
clubs:=((proto_data(obj_pid(rndcritter),cr_fid) != FID_NMMAXX) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NFMAXX) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_HMBMET) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NFMETL) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMCOPP) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NAVGUL) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NAGHUL) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMMEXI) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMLTHR) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMGANG) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMRGNG) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_MAMTNT) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_MAMTN2) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NAPOWR));
spear:=((proto_data(obj_pid(rndcritter),cr_fid) != FID_NMMAXX) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_HMBMET) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMCOPP) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NAVGUL) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMMEXI) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMGANG) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMRGNG) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_MAMTNT) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_MAMTN2) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NAPOWR));
knife:=((proto_data(obj_pid(rndcritter),cr_fid) != FID_NMCOPP) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMLTHR) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_MAMTNT) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_MAMTN2) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NAPOWR));
thrown:=((proto_data(obj_pid(rndcritter),cr_fid) != FID_NMMAXX) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NFMETL) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NFMAXX) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMLTHR) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMLTHR) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NAPOWR));
sledge:=((proto_data(obj_pid(rndcritter),cr_fid) != FID_NMMAXX) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NFMAXX) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NFMETL) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMCOPP) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NAVGUL) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NAGHUL) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMMEXI) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMLTHR) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMGANG) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NMRGNG) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_MAMTNT) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_MAMTN2) and (proto_data(obj_pid(rndcritter),cr_fid) != FID_NAPOWR));
Then comes the most important part: establishing who gets what class of weapon. I do so on the basis of how high tech the area is, combined with the critter's experience value.
[spoiler:3c4f006f02]
Code:
if (( ((((cur_town == AREA_VAULT_CITY) and (cur_map_index != MAP_VAULTCITY_COURTYARD)) or (cur_town == AREA_NCR) or (cur_town == AREA_SAN_FRANCISCO))*290) + (((cur_town == AREA_NAVARRO) or (cur_town == AREA_THE_ENCLAVE) or (cur_town == AREA_MILITARY_BASE))*420) + (((cur_map_index == MAP_VAULTCITY_COURTYARD) or (cur_map_index == MAP_REDDING_WANAMINGO_ENT) or (cur_town == AREA_GECKO) or (cur_town == AREA_BROKEN_HILLS) or (cur_town == AREA_NEW_RENO) or (cur_town == AREA_VAULT_15) or (cur_town == AREA_RAIDERS) or (cur_town == AREA_RENO_STABLES))*190) + (((cur_town == AREA_DEN) or (cur_town == AREA_GHOST_TOWN) or (cur_town == AREA_MODOC) or ((cur_town == AREA_REDDING) and (cur_map_index != MAP_REDDING_WANAMINGO_ENT)))*110) + (get_proto_data(obj_pid(rndcritter), 392)/5)) > 570) then
rollmod:=570;
else
rollmod:=( ((((cur_town == AREA_VAULT_CITY) and (cur_map_index != MAP_VAULTCITY_COURTYARD)) or (cur_town == AREA_NCR) or (cur_town == AREA_SAN_FRANCISCO))*290) + (((cur_town == AREA_NAVARRO) or (cur_town == AREA_THE_ENCLAVE) or (cur_town == AREA_MILITARY_BASE))*420) + (((cur_map_index == MAP_VAULTCITY_COURTYARD) or (cur_map_index == MAP_REDDING_WANAMINGO_ENT) or (cur_town == AREA_GECKO) or (cur_town == AREA_BROKEN_HILLS) or (cur_town == AREA_NEW_RENO) or (cur_town == AREA_VAULT_15) or (cur_town == AREA_RAIDERS) or (cur_town == AREA_RENO_STABLES))*190) + (((cur_town == AREA_DEN) or (cur_town == AREA_GHOST_TOWN) or (cur_town == AREA_MODOC) or ((cur_town == AREA_REDDING) and (cur_map_index != MAP_REDDING_WANAMINGO_ENT)))*110) + (get_proto_data(obj_pid(rndcritter), 392)/5));
Then, if the critter is not a melee/unarmed character, the roll is made for his ranged weapon. I simply made a list of the ranged weapons from "bad" to "good", but let me know if you think the order should be different.
[spoiler:3c4f006f02]
Code:
if (has_skill(rndcritter, SKILL_ENERGY_WEAPONS) >= has_skill(rndcritter, SKILL_MELEE)) or (has_skill(rndcritter, SKILL_BIG_GUNS) >= has_skill(rndcritter, SKILL_MELEE)) or (has_skill(rndcritter, SKILL_SMALL_GUNS) >= has_skill(rndcritter, SKILL_MELEE)) then begin
primary_roll:=random(rollmod, 150+rollmod);
if (primary_roll ^ 70) and (rifle == 1) then
primary := create_object( PID_SPRINGER_RIFLE, 0, 0 );
else if (primary_roll ^ 90) and (pistol == 1) then
primary := create_object( PID_9MM_MAUSER, 0, 0 );
else if (primary_roll ^ 170) and (pistol == 1) then
primary := create_object( PID_10MM_PISTOL, 0, 0 );
else if (primary_roll ^ 190) and (pistol == 1) then
primary := create_object( PID_44_MAGNUM_REVOLVER, 0, 0 );
else if (primary_roll ^ 205) and (pistol == 1) then
primary := create_object( PID_DESERT_EAGLE, 0, 0 );
else if (primary_roll ^ 220) and (smg == 1) then
primary := create_object( PID_14MM_PISTOL, 0, 0 );
else if (primary_roll ^ 245) and (smg == 1) then
primary := create_object( PID_10MM_SMG, 0, 0 );
else if (primary_roll ^ 265) and (rifle == 1) then
primary := create_object( PID_SHOTGUN, 0, 0 );
else if (primary_roll ^ 280) and (rifle == 1) then
primary := create_object( PID_SAWED_OFF_SHOTGUN, 0, 0 );
else if (primary_roll ^ 290) and (rifle == 1) then
primary := create_object( PID_TOMMY_GUN, 0, 0 );
else if (primary_roll ^ 305) and (smg == 1) then
primary := create_object( PID_GREASE_GUN, 0, 0 );
else if (primary_roll ^ 325) and (rifle == 1) then
primary := create_object( PID_ASSAULT_RIFLE, 0, 0 );
else if (primary_roll ^ 345) and (rifle == 1) then
primary := create_object( PID_HUNTING_RIFLE, 0, 0 );
else if (primary_roll ^ 365) and (rifle == 1) then
primary := create_object( PID_FN_FAL, 0, 0 );
else if (primary_roll ^ 375) and (smg == 1) then
primary := create_object( PID_HK_P90C, 0, 0 );
else if (primary_roll ^ 390) and (pistol == 1) then
primary := create_object( PID_NEEDLER_PISTOL, 0, 0 );
else if (primary_roll ^ 405) and (pistol == 1) and (has_skill(rndcritter, SKILL_ENERGY_WEAPONS) > 70) then
primary := create_object( PID_LASER_PISTOL, 0, 0 );
else if (primary_roll ^ 420) and (rifle == 1) then
primary := create_object( PID_COMBAT_SHOTGUN, 0, 0 );
else if (primary_roll ^ 430) and (rifle == 1) then
primary := create_object( PID_HK_CAWS, 0, 0 );
else if (primary_roll ^ 440) and (pistol == 1) and (has_skill(rndcritter, SKILL_ENERGY_WEAPONS) > 70) then
primary := create_object( PID_PLASMA_PISTOL, 0, 0 );
else if (primary_roll ^ 450) and (rifle == 1) and (get_critter_stat(rndcritter, STAT_pe) > 7) then
primary := create_object( PID_SNIPER_RIFLE, 0, 0 );
else if (primary_roll ^ 460) and (rifle == 1) then
primary := create_object( PID_PANCOR_JACKHAMMER, 0, 0 );
else if (primary_roll ^ 470) and (smg == 1) then
primary := create_object( PID_HK_G11, 0, 0 );
else if (primary_roll ^ 480) and (smg == 1) then
primary := create_object( PID_223_PISTOL, 0, 0 );
else if (primary_roll ^ 490) and (rifle == 1) then
primary := create_object( PID_INDEPENDENT, 0, 0 );
else if (primary_roll ^ 505) and (minigun == 1) and (has_skill(rndcritter, SKILL_BIG_GUNS) > 70) then
primary := create_object( PID_MINIGUN, 0, 0 );
else if (primary_roll ^ 515) and (big_gun == 1) and (has_skill(rndcritter, SKILL_BIG_GUNS) > 70) then
primary := create_object( PID_LIGHT_SUPPORT_WEAPON, 0, 0 );
else if (primary_roll ^ 525) and (big_gun == 1)and (has_skill(rndcritter, SKILL_BIG_GUNS) > 70) then
primary := create_object( PID_M60, 0, 0 );
else if (primary_roll ^ 540) and (big_gun == 1) and (has_skill(rndcritter, SKILL_BIG_GUNS) > 70) then
primary := create_object( PID_FLAMER, 0, 0 );
else if (primary_roll ^ 550) and (pistol == 1) then
primary := create_object( PID_PK12_GAUSS_PISTOL, 0, 0 );
else if (primary_roll ^ 560) and (big_gun == 1) and (has_skill(rndcritter, SKILL_BIG_GUNS) > 70) then
primary := create_object( PID_BOZAR, 0, 0 );
else if (primary_roll ^ 570) and (pistol == 1) and (has_skill(rndcritter, SKILL_ENERGY_WEAPONS) > 70) then
primary := create_object( PID_YK32_PULSE_PISTOL, 0, 0 );
else if (primary_roll ^ 585) and (minigun == 1) and (has_skill(rndcritter, SKILL_BIG_GUNS) > 70) then
primary := create_object( PID_AVENGER_MINIGUN, 0, 0 );
else if (primary_roll ^ 600) and (big_gun == 1) and (has_skill(rndcritter, SKILL_ENERGY_WEAPONS) > 70) then
primary := create_object( PID_LASER_RIFLE, 0, 0 );
else if (primary_roll ^ 610) and (big_gun == 1) and (has_skill(rndcritter, SKILL_ENERGY_WEAPONS) > 70) then
primary := create_object( PID_PLASMA_RIFLE, 0, 0 );
else if (primary_roll ^ 625) and (rifle == 1) then
primary := create_object( PID_M72_GAUSS_RIFLE, 0, 0 );
else if (primary_roll ^ 655) and (rocket_launcher == 1) and (has_skill(rndcritter, SKILL_BIG_GUNS) > 70) then
primary := create_object( PID_ROCKET_LAUNCHER, 0, 0 );
else if (primary_roll ^ 665) and (minigun == 1) and (has_skill(rndcritter, SKILL_BIG_GUNS) > 70) then
primary := create_object( PID_VINDICATOR_MINIGUN, 0, 0 );
else if (primary_roll ^ 680) and (minigun == 1) and (has_skill(rndcritter, SKILL_ENERGY_WEAPONS) > 70) then
primary := create_object( PID_GATLING_LASER, 0, 0 );
else if (primary_roll ^ 700) and (rifle == 1) and (has_skill(rndcritter, SKILL_ENERGY_WEAPONS) > 70) then
primary := create_object( PID_YK42B_PULSE_RIFLE, 0, 0 );
else if (primary_roll ^ 710) and (big_gun == 1) and (has_skill(rndcritter, SKILL_BIG_GUNS) > 70) then
primary := create_object( PID_IMPROVED_FLAMETHROWER, 0, 0 );
else if (primary_roll ^= 720) and (big_gun == 1) and (has_skill(rndcritter, SKILL_ENERGY_WEAPONS) > 70) then
primary := create_object( PID_TURBO_PLASMA_RIFLE, 0, 0 );
Then the ammo type gets randomized if there are multiple possibilities (e.g. 10MM AP/JHP)
[spoiler:3c4f006f02]
Code:
if (get_weapon_ammo_pid(primary) == PID_5MM_JHP) or (get_weapon_ammo_pid(primary) == PID_5MM_AP) then begin
set_weapon_ammo_pid(primary, random(PID_5MM_JHP,PID_5MM_AP));
end else if (get_weapon_ammo_pid(primary) == PID_10MM_JHP) or (get_weapon_ammo_pid(primary) == PID_10MM_AP) then begin
set_weapon_ammo_pid(primary, random(PID_10MM_JHP,PID_10MM_AP));
end else if (get_weapon_ammo_pid(primary) == PID_HN_NEEDLER_CARTRIDGE) or (get_weapon_ammo_pid(primary) == PID_HN_AP_NEEDLER_CARTRIDGE) then begin
set_weapon_ammo_pid(primary, random(PID_HN_NEEDLER_CARTRIDGE,PID_HN_AP_NEEDLER_CARTRIDGE));
end else if (get_weapon_ammo_pid(primary) == PID_EXPLOSIVE_ROCKET) or (get_weapon_ammo_pid(primary) == PID_ROCKET_AP) then begin
if random(1,50) ^ 26 then
set_weapon_ammo_pid(primary, PID_EXPLOSIVE_ROCKET);
else
set_weapon_ammo_pid(primary, PID_ROCKET_AP);
end else if (get_weapon_ammo_pid(primary) == PID_9MM_BALL) or (get_weapon_ammo_pid(primary) == PID_9MM_AMMO) then begin
if random(1,50) ^ 26 then
set_weapon_ammo_pid(primary, PID_9MM_BALL);
else
set_weapon_ammo_pid(primary, PID_9MM_AMMO);
end else if (get_weapon_ammo_pid(primary) == PID_44_MAGNUM_JHP) or (get_weapon_ammo_pid(primary) == PID_44_FMJ_MAGNUM) then begin
if random(1,50) ^ 26 then
set_weapon_ammo_pid(primary, PID_44_MAGNUM_JHP);
else
set_weapon_ammo_pid(primary, PID_44_FMJ_MAGNUM);
end
Next, the ammount of ammo gets determined, based on the same factors as for the weapon itself. The possible outcome ranges from the weapon having a 1/4 filled magazine to a maximum of five additional ammo stacks (so that'd probably only be one extra magazine in the old system).
[spoiler:3c4f006f02]
Code:
ammo_roll:=random(rollmod, 430+rollmod);
if (ammo_roll ^ 351) and (obj_pid(primary) == PID_SHOTGUN or obj_pid(primary) == PID_SAWED_OFF_SHOTGUN or obj_pid(primary) == PID_SPRINGER_RIFLE) then
ammo_roll:=351;
if (ammo_roll ^ 101) then begin
set_weapon_ammo_count(primary, (get_weapon_ammo_count(primary)/4));
end else if (ammo_roll ^ 201) then begin
set_weapon_ammo_count(primary, (get_weapon_ammo_count(primary)/2));
end else if (ammo_roll ^ 351) then begin
set_weapon_ammo_count(primary, (get_weapon_ammo_count(primary) - (get_weapon_ammo_count(primary)/4)));
end else if (ammo_roll ^ 501) then begin
end else if (ammo_roll ^ 601) then begin
ammo1 := create_object( get_weapon_ammo_pid(primary), 0, 0 );
add_obj_to_inven(rndcritter, ammo1);
end else if (ammo_roll ^ 701) then begin
ammo1 := create_object( get_weapon_ammo_pid(primary), 0, 0 );
ammo2 := create_object( get_weapon_ammo_pid(primary), 0, 0 );
add_obj_to_inven(rndcritter, ammo1);
add_obj_to_inven(rndcritter, ammo2);
end else if (ammo_roll ^ 801) then begin
ammo1 := create_object( get_weapon_ammo_pid(primary), 0, 0 );
ammo2 := create_object( get_weapon_ammo_pid(primary), 0, 0 );
ammo3 := create_object( get_weapon_ammo_pid(primary), 0, 0 );
add_obj_to_inven(rndcritter, ammo1);
add_obj_to_inven(rndcritter, ammo2);
add_obj_to_inven(rndcritter, ammo3);
end else if (ammo_roll ^ 901) then begin
ammo1 := create_object( get_weapon_ammo_pid(primary), 0, 0 );
ammo2 := create_object( get_weapon_ammo_pid(primary), 0, 0 );
ammo3 := create_object( get_weapon_ammo_pid(primary), 0, 0 );
ammo4 := create_object( get_weapon_ammo_pid(primary), 0, 0 );
add_obj_to_inven(rndcritter, ammo1);
add_obj_to_inven(rndcritter, ammo2);
add_obj_to_inven(rndcritter, ammo3);
add_obj_to_inven(rndcritter, ammo4);
end else begin
ammo1 := create_object( get_weapon_ammo_pid(primary), 0, 0 );
ammo2 := create_object( get_weapon_ammo_pid(primary), 0, 0 );
ammo3 := create_object( get_weapon_ammo_pid(primary), 0, 0 );
ammo4 := create_object( get_weapon_ammo_pid(primary), 0, 0 );
ammo5 := create_object( get_weapon_ammo_pid(primary), 0, 0 );
add_obj_to_inven(rndcritter, ammo1);
add_obj_to_inven(rndcritter, ammo2);
add_obj_to_inven(rndcritter, ammo3);
add_obj_to_inven(rndcritter, ammo4);
add_obj_to_inven(rndcritter, ammo5);
end
Next, the ranged critter gets a possible (weaker) roll for an additional sidearm, whose ammo count is always 1/2 to 3/4 empty.
[spoiler:3c4f006f02]
Code:
if (primary_roll >= 170) and (random(1,100) > 50) and (pistol == 1) then begin
if (primary_roll ^= 220) then begin
if random(1,50) ^ 20 then
tertiary := create_object( PID_9MM_MAUSER, 0, 0 );
else
tertiary := create_object( PID_10MM_PISTOL, 0, 0 );
end else if (primary_roll ^= 550) then begin
tertiary_roll:=random(1, 100);
if (tertiary_roll ^ 34) then
tertiary := create_object( PID_10MM_PISTOL, 0, 0 );
else if (tertiary_roll ^ 67) then
tertiary := create_object( PID_44_MAGNUM_REVOLVER, 0, 0 );
else
tertiary := create_object( PID_DESERT_EAGLE, 0, 0 );
end else begin
tertiary_roll:=random(1, 100);
if (tertiary_roll ^ 26) and (has_skill(rndcritter, SKILL_ENERGY_WEAPONS) > 70) then
tertiary := create_object( PID_PLASMA_PISTOL, 0, 0 );
else if (tertiary_roll ^ 51) and (has_skill(rndcritter, SKILL_ENERGY_WEAPONS) > 70) then
tertiary := create_object( PID_LASER_PISTOL, 0, 0 );
else if (tertiary_roll ^ 76) then
tertiary := create_object( PID_NEEDLER_PISTOL, 0, 0 );
else
tertiary := create_object( PID_PK12_GAUSS_PISTOL, 0, 0 );
end
if (get_weapon_ammo_pid(tertiary) == PID_10MM_JHP) or (get_weapon_ammo_pid(tertiary) == PID_10MM_AP) then begin
set_weapon_ammo_pid(tertiary, random(PID_10MM_JHP,PID_10MM_AP));
end else if (get_weapon_ammo_pid(tertiary) == PID_HN_NEEDLER_CARTRIDGE) or (get_weapon_ammo_pid(tertiary) == PID_HN_AP_NEEDLER_CARTRIDGE) then begin
set_weapon_ammo_pid(tertiary, random(PID_HN_NEEDLER_CARTRIDGE,PID_HN_AP_NEEDLER_CARTRIDGE));
end else if (get_weapon_ammo_pid(tertiary) == PID_9MM_BALL) or (get_weapon_ammo_pid(tertiary) == PID_9MM_AMMO) then begin
if random(1,50) ^ 26 then
set_weapon_ammo_pid(tertiary, PID_9MM_BALL);
else
set_weapon_ammo_pid(tertiary, PID_9MM_AMMO);
end else if (get_weapon_ammo_pid(tertiary) == PID_44_MAGNUM_JHP) or (get_weapon_ammo_pid(tertiary) == PID_44_FMJ_MAGNUM) then begin
if random(1,50) ^ 26 then
set_weapon_ammo_pid(tertiary, PID_44_MAGNUM_JHP);
else
set_weapon_ammo_pid(tertiary, PID_44_FMJ_MAGNUM);
end
set_weapon_ammo_count(tertiary, (get_weapon_ammo_count(tertiary)/random(2,4)));
add_obj_to_inven(rndcritter, tertiary);
end
Next, the melee character get a roll; first the bruisers (clubs, sledges, brass knuckles, etc.), then the agile fighters (knives and spears). Energy melee weapons get an ammo roll.
[spoiler:3c4f006f02]
Code:
if (get_critter_stat(rndcritter, STAT_st) > 6) and (critter_kill_type(rndcritter) != KILL_TYPE_women_kills) then begin
if (primary_roll ^= 280) then begin
secondary_roll:=random(1, 80);
if (secondary_roll ^ 16) and (clubs == 1) then
secondary := create_object( PID_CLUB, 0, 0 );
else if (secondary_roll ^ 31) and (clubs == 1) then
secondary := create_object( PID_CROWBAR, 0, 0 );
else if (secondary_roll ^ 46) and (sledge == 1) then
secondary := create_object( PID_SLEDGEHAMMER, 0, 0 );
else
secondary := create_object( PID_BRASS_KNUCKLES, 0, 0 );
end else if (primary_roll ^= 500) then begin
secondary_roll:=random(1, 80);
if (secondary_roll ^ 21) and (clubs == 1) then
secondary := create_object( PID_CATTLE_PROD, 0, 0 );
else if (secondary_roll ^ 41) and (sledge == 1) then
secondary := create_object( PID_SLEDGEHAMMER, 0, 0 );
else
secondary := create_object( PID_SPIKED_KNUCKLES, 0, 0 );
end else begin
if (random(1,100) ^ 51) and (sledge == 1) then
secondary := create_object( PID_SUPER_SLEDGE, 0, 0 );
else
secondary := create_object( PID_POWER_FIST, 0, 0 );
end
end else begin
if (primary_roll ^= 120) then begin
if (random(1,100) ^ 51) and (knife == 1) then
secondary := create_object( PID_SHIV, 0, 0 );
else if (spear == 1) then
secondary := create_object( PID_SHARPENED_POLE, 0, 0 );
else
secondary := create_object( PID_SHIV, 0, 0 );
end else if (primary_roll ^= 240) then begin
if (random(1,100) ^ 51) and (knife == 1) then
secondary := create_object( PID_KNIFE, 0, 0 );
else if (spear == 1) then
secondary := create_object( PID_SPEAR, 0, 0 );
else
secondary := create_object( PID_KNIFE, 0, 0 );
end else if (primary_roll ^= 370) then begin
secondary_roll:=random(1, 80);
if (secondary_roll ^ 41) and (spear == 1) then
secondary := create_object( PID_SHARP_SPEAR, 0, 0 );
else if (knife == 1) then
secondary := create_object( PID_SWITCHBLADE, 0, 0 );
else
secondary := create_object( PID_SHARP_SPEAR, 0, 0 );
end else if (primary_roll ^= 500) then begin
if (knife == 1) then
secondary := create_object( PID_COMBAT_KNIFE, 0, 0 );
end else begin
if (knife == 1) then
secondary := create_object( PID_RIPPER, 0, 0 );
end
end
Next, both ranged and melee characters get a possible (1/5 or so chance, and only if they have at least some throwing skill) roll for a throwing weapons. With throwing knives there'll be more chance of getting additional ones than with grenades and such.
[spoiler:3c4f006f02]
Code:
if (random(1,100) > 80) and thrown == 1 and (has_skill(rndcritter, SKILL_THROWING) > 59) then begin
if primary_roll ^ 200 then begin
if knife == 1 then begin
quaternary := create_object( PID_THROWING_KNIFE, 0, 0 );
add_obj_to_inven(rndcritter, quaternary);
if (random(1,100) > 30) then begin
quaternary := create_object( PID_THROWING_KNIFE, 0, 0 );
add_obj_to_inven(rndcritter, quaternary);
if (random(1,100) > 30) then begin
quaternary := create_object( PID_THROWING_KNIFE, 0, 0 );
add_obj_to_inven(rndcritter, quaternary);
if (random(1,100) > 30) then begin
quaternary := create_object( PID_THROWING_KNIFE, 0, 0 );
add_obj_to_inven(rndcritter, quaternary);
if (random(1,100) > 30) then begin
quaternary := create_object( PID_THROWING_KNIFE, 0, 0 );
add_obj_to_inven(rndcritter, quaternary);
end
end
end
end
end
end else if primary_roll ^ 400 then begin
if random(1,100) ^ 51 and knife == 1 then begin
quaternary := create_object( PID_THROWING_KNIFE, 0, 0 );
add_obj_to_inven(rndcritter, quaternary);
if (random(1,100) > 30) then begin
quaternary := create_object( PID_THROWING_KNIFE, 0, 0 );
add_obj_to_inven(rndcritter, quaternary);
if (random(1,100) > 30) then begin
quaternary := create_object( PID_THROWING_KNIFE, 0, 0 );
add_obj_to_inven(rndcritter, quaternary);
if (random(1,100) > 30) then begin
quaternary := create_object( PID_THROWING_KNIFE, 0, 0 );
add_obj_to_inven(rndcritter, quaternary);
if (random(1,100) > 30) then begin
quaternary := create_object( PID_THROWING_KNIFE, 0, 0 );
add_obj_to_inven(rndcritter, quaternary);
end
end
end
end
end
Finally, both character types get a possible (weaker) roll for a (additional, in the case of melee characters) melee weapon.
[spoiler:3c4f006f02]
Code:
end else if (random(1,100) > 30) and not ((proto_data(obj_pid(rndcritter),cr_fid) == FID_HAPOWR) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_HANPWR) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_MAMTNT) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_MAMTN2) or (proto_data(obj_pid(rndcritter),cr_fid) == FID_NAPOWR)) then begin
if primary_roll ^ 270 then begin
quaternary_roll:=random(1,100);
if (quaternary_roll ^ 21) and (knife == 1) then
quaternary := create_object( PID_SHIV, 0, 0 );
else if (quaternary_roll ^ 41) and (clubs == 1) then
quaternary := create_object( PID_CLUB, 0, 0 );
else if (quaternary_roll ^ 61) and (knife == 1) then
quaternary := create_object( PID_KNIFE, 0, 0 );
else if (quaternary_roll ^ 81) then
quaternary := create_object( PID_BRASS_KNUCKLES, 0, 0 );
else if (clubs == 1) then
quaternary := create_object( PID_CROWBAR, 0, 0 );
end else if primary_roll ^ 380 then begin
quaternary_roll:=random(1,100);
if random(1,50) ^ 25 then
quaternary := create_object( PID_SPIKED_KNUCKLES, 0, 0 );
else if (knife == 1) then
quaternary := create_object( PID_SWITCHBLADE, 0, 0 );
else
quaternary := create_object( PID_SPIKED_KNUCKLES, 0, 0 );
end else begin
if (knife == 1) then
quaternary := create_object( PID_COMBAT_KNIFE, 0, 0 );
end
add_obj_to_inven(rndcritter, quaternary);
Note that all critters immediately wield their primary weapon, so you sometimes get a bit strange scene upon first entering a map of characters holstering their destroyed weapons and unholstering their new ones, but nothing too bad.