Many mods now seem to be just edited Guns and jeeps with the color, damage, or model changed and all the effects left the same. Since people use "Find and Replace" to edit the file, people end up with about 10 identical sounds all calling gunShot1.wav using AudioClose3d and preloading it. And 20 trail emitters all exactly the same. And lots of unused SOMETHINGshellDebris. Which eventually causes people to run over the datablock limit and start crashing and complaining on forum.
The trouble is, just using the same names as existing things can cause errors.
The example I'll use for this is a nonexistant "UberGun" which is exactly the same as the Gun with except it has a different color.
datablock ShapeBaseImageData(ubergunImage)
{
...stuff...
projectile = gunProjectile;
colorShiftColor = "1 0 0 1";
...stuff...
}
Yes, it could use the (uberGunImage : gunImage) but that can be complicated and causes the same errors if the datablocks don't exist.
This works fine, provided the Weapon_Gun is actually enabled. If it isn't, you start getting errors:ERROR: gunProjectile is not a member of the "Projectile" datablock class.
How do you fix this?
Adding exec("Add-Ons/Weapon_Gun.cs"); to the top of the file works. But, what if you don't WANT the gun enabled and you only want the UberGun? Using the exec like that will cause both to appear in the menu.
This code would work:
exec("./Weapon_Gun.cs");
if($AddOn__Weapon_Gun $= "-1"){schedule(1000,0,eval,"gunitem.uiname = \"\";");}
It executes the Gun and then if it isn't enabled, removes it from the wrench and minigame lists.
But if you used that in a LOT of edited gun mods...
Executing Add-Ons/Weapon_UberGun.cs
Executing Add-Ons/Weapon_Gun.cs
Executing Add-Ons/Weapon_DeathGun.cs
Executing Add-Ons/Weapon_Gun.cs
Executing Add-Ons/Weapon_FastFireGun.cs
Executing Add-Ons/Weapon_Gun.cs
... It executes the gun every single time one of these mods is executed even though the necessary datablocks already exist, which looks very untidy. Now, if you don't care about the console this works fine. Chances are, if you are coding anything other than a generic weapon then you do care about errors, echos and unneeded execs. So, I come to the final code:
if(!isObject(gunProjectile)){exec("./Weapon_Gun.cs");}
if($AddOn__Weapon_Gun $= "-1"){schedule(1000,0,eval,"gunitem.uiname = \"\";");}
It checks if the gun stuff already exists before executing it. Then:Executing Add-Ons/Weapon_UberGun.cs
Executing Add-Ons/Weapon_Gun.cs
Executing Add-Ons/Weapon_DeathGun.cs
Executing Add-Ons/Weapon_FastFireGun.cs
By the way, this doesn't only have to be used for weapons. For instance, the Trap Brick: Laser Trigger uses an "Alarm" particle above it. Rather than waste datablocks by creating new particles or copying them from the Emote_Alarm.cs file, I used this:
if(!isObject(alarmEmitter)){exec("./Emote_Alarm.cs");}
if($AddOn__Weapon_Alarm $= "-1"){schedule(1000,0,eval,"function servercmdAlarm(){}");}
It exec's the alarm so I can use that emitter but if the alarm emote isn't activated it disables the /Alarm command.
It might not seem much to add, but I think it makes things a lot easier not to have a hundred random emitters all doing exactly the same thing. For those who like hosting servers with lots of add-ons, using this in a few of them could help you a lot.