Explosion SWep
From GMod Wiki
Lua: Explosion SWep How-To |
Description: | Tutorial on how to make a SWep that creates an explosion where you shoot. |
Original Author: | cheesylard |
Created: | April 1st, 2008 |
A new tutorial: how to make a SWep that makes explosions!!!
This tutorial is kind of... bad. Maybe some people can make little improvements or something, I dunno.
Contents |
Where to put your files!
If you put your files on your desktop, Garry's Mod would not open them, because they aren't in the garrysmod folder! You need to organize your files in order to get your Lua codes to work.
Okay, so go to:
C:\Program Files\Steam\SteamApps\cheesylard\garrysmod\garrysmod\lua
Replace cheesylard with the steam account name where you have garrysmod installed. This could be john334 or mike389.
Okay, this is where all of the Lua files are stored. All of the weapons, entites, and effects.
Since you are making a weapon, click on the weapons folder. If it isn't there, create it!
Now, if you have installed some mods, you might see some things like cse_awp or cse_base or maybe some other stuff. Just ignore it. Make a new folder, you can name it whatever you want, but make sure it doesn't have any spaces in it.
I'm going to name mine weapon_explodinator.
The files
There are generally 3 files inside this folder, which are used by garrysmod. One is only used by the server, like "Johns Sandbox server", one is only used by the client, the person joining the server, and one used by both.
These are called init.lua (server), cl_init.lua (client), and shared.lua(both).
Okay, create these, and I'll tell you what to do with them. (To save a notebook file as lua change the option to all files and put .lua on the end of the filename.)
To do it, just open notepad, and save a blank text file as init.lua, then do save as again, do shared.lua, then save as again, then do cl_init.lua.
This is what it should look like so far:
Setting weapon properties
Okay, open init.lua with Notepad, and put the following code in there, I will explain what it does:
init.lua
AddCSLuaFile ("cl_init.lua"); AddCSLuaFile ("shared.lua"); include ("shared.lua"); SWEP.Weight = 5; SWEP.AutoSwitchTo = false; SWEP.AutoSwitchFrom = false;
The AddCSLuaFile() function tells the server to make the person who connects to the server download the file it specifies. If it isn't in there, the client would just get an inconsistency error and would never be able to join the server.
The Include() function is basically as if you copy and pasted the specified file right into the code.
You usually don't want to edit SWEP.Weight and the other ones, as it is courteous to leave them as is.
cl_init.lua
Now, open cl_init.lua.
include ("shared.lua"); SWEP.PrintName = "My EXPLODING gun!"; SWEP.Slot = 2; SWEP.SlotPos = 4; SWEP.DrawAmmo = true; SWEP.DrawCrosshair = true;
These are kind of obvious, the SWEP.PrintName tells GMod to print the name of the SWEP in the SWep menu, and SWEP.DrawCrosshair decides whether or not to have a crosshair on the SWep.
Inside the shared.lua file; we define numerous properties and functions that Garry's Mod will look for when using the SWEP weapon; for example when the client asks to fire the weapon, Garry's Mod will execute the PrimaryAttack() function.
Okay, now open shared.lua.
SWEP.Author = "yourname" SWEP.Contact = "[email protected]" SWEP.Purpose = "Blow up people, duh!" SWEP.Instructions = "Primary to fire a bullet, Secondary to make an explosion where you are pointing" SWEP.Category = "Explosion SWeps"
This stuff is used for when you are selecting the weapon in the SWeps menu.
SWEP.Category tells Garry's Mod to put the gun in a certain category. Like, you can see all of the counter strike weapons in the Counter-Strike category, and others.
SWEP.Spawnable = false; SWEP.AdminSpawnable = true;
SWEP.Spawnable and SWEP.AdminSpawnable determine who can spawn it. If you only have AdminSpawnable on, only admins can spawn it, if you have both on, everyone can spawn it, and if you have both off, then nobody can spawn it (Used for weapon bases).
SWEP.ViewModel = "models/weapons/v_357.mdl"; SWEP.WorldModel = "models/weapons/w_357.mdl";
This allows you to select the model used to display the weapon. The View model is the one you see in first person view (the hands holding the gun), the world model is used when someone is looking at you (another player)
SWEP.Primary.ClipSize = 8; SWEP.Primary.DefaultClip = 20; SWEP.Primary.Automatic = false; SWEP.Primary.Ammo = "357"; SWEP.Secondary.ClipSize = -1; SWEP.Secondary.DefaultClip = -1; SWEP.Secondary.Automatic = false; SWEP.Secondary.Ammo = "none";
This stuff is used for weapons with clips. We are going to make the Primary fire bullets, but the secondary do not. The ClipSize determines how many bullets are in a clip (when you reload), and DefaultClip tells how much extra ammo you have.
SWEP functions
This is the hard (and cool) part. This is where the actual exploding and shooting parts happen. These are stored inside weapon functions, which are used when Garry's Mod tells the SWep it's shooting, reloading, etc.
The significant functions are:
SWEP:Reload() : This is used when you press the reload key.
SWEP:Think() : This function is run every server tick, basically all the time.
SWEP:PrimaryAttack() : This is run whenever the primary attack on the weapon is done.
SWEP:SecondaryAttack() : Done whenever the secondary attack is done.
SWEP:Deploy(): Called when you take the gun out.
SWEP:Holster(): Called when you put the gun away.
Variables
Before doing anything, we want to make variables that are used when called for, so they are easier to edit, instead of going into each function and changing it.
SWEP.Sound = Sound ("weapon_357.Single") SWEP.Damage = 50 SWEP.Spread = 0.02 SWEP.NumBul = 1 SWEP.Delay = 0.7 SWEP.Force = 3
Unused functions
Here, we are not going to Use Think, Deploy or Holster, so we are going to leave them empty, like so:
function SWEP:Deploy() return true end function SWEP:Holster() return true end function SWEP:Think() end
I put the return true parts in there because we need to let them know that you are allowed to put the gun away.
Comments
Comments are used to show what something does, or to mark a spot where you are coding. To make a comment, just put a -- in front of a line, and Garry's Mod will ignore it.
Single-Line Comment Example:
-- I made a single line comment!
Please note that in Lua, // is not the proper way to comment lines; rather, use -- for commenting.
If you want to make a comment with more than one line, there are two methods:
Multi-Line Method One: /* COMMENT HERE */.
Example:
/*
I made a multi line comment!
OMG, another line!
And another!
*/
Multi-Line Method Two: --[[
Example:
--[[
I made another multi-line comment!
AND ANOTHER LINE!
and another!
etc
]]
Now for the actual coding
Yay! I will now show you how to make an explosion, just read the comments, and that will explain most of it.
SecondaryAttack
function SWEP:SecondaryAttack() -- when secondary attack happens -- Make sure we can shoot first if ( !self:CanPrimaryAttack() ) then return end local eyetrace = self.Owner:GetEyeTrace(); -- this gets where you are looking. The SWep is making an explosion where you are LOOKING, right? self:EmitSound ( self.Sound ) -- this makes the sound, which I specified earlier in the code self.BaseClass.ShootEffects (self); -- this makes the shooting animation for the 357 for view model and world model. local explode = ents.Create( "env_explosion" ) -- creates the explosion explode:SetPos( eyetrace.HitPos ) -- this creates the explosion through your self.Owner:GetEyeTrace, which is why I put eyetrace in front explode:SetOwner( self.Owner ) -- this sets you as the person who made the explosion explode:Spawn() --this actually spawns the explosion explode:SetKeyValue( "iMagnitude", "220" ) -- the magnitude explode:Fire( "Explode", 0, 0 ) explode:EmitSound( "weapon_AWP.Single", 400, 400 ) -- the sound for the explosion, and how far away it can be heard self:SetNextPrimaryFire( CurTime() + self.Delay ) self:SetNextSecondaryFire( CurTime() + self.Delay ) -- this sets the delay for the next primary and secondary fires. self:TakePrimaryAmmo(1) -- removes 1 ammo from our clip end -- telling Gmod that it's the end of the function
The comments should explain it. Pretty simple, right? If you don't have CS:S I would change the sound of the explosion.
Also, notice how when I refrenced the sound, I put self.Sound instead of SWEP.Sound. Why you have to put self instead of SWEP in order for it to work, I don't know. Just remember when refrencing in functions, put self. in front of it, and when outside of functions, put SWEP. in front of it.
Also, the local eyetrace part, you can name whatever you want. You could name it chicken for all I care. Just remember to make sure the references to it are correct!
Now for the shooting part:
PrimaryAttack
function SWEP:PrimaryAttack() -- when +attack1 happens -- Make sure we can shoot first if ( !self:CanPrimaryAttack() ) then return end local bullet = {} -- creates a table for the properties of the bullet bullet.Num = self.NumBul -- number of bullets you are shooting bullet.Src = self.Owner:GetShootPos() -- Source, where you are standing bullet.Dir = self.Owner:GetAimVector() -- direction of bullet, where you are looking bullet.Spread = Vector( self.Spread, self.Spread, 0 ) -- spread of bullet, how accurate it is bullet.Tracer = 0 -- this doesn't really affect anything bullet.Force = self.Force -- how powerful it is bullet.Damage = self.Damage -- how much damage it does to people bullet.AmmoType = self.Primary.Ammo -- what type of ammo you are using self.Owner:FireBullets( bullet ) -- actually shoots the bullet. self:EmitSound ( self.Sound ) -- this makes the sound, which I specified earlier in the code self.BaseClass.ShootEffects (self); -- this makes the shooting animation for the 357 for view model and world model self:SetNextPrimaryFire( CurTime() + self.Delay ) self:SetNextSecondaryFire( CurTime() + self.Delay ) -- this sets the delay for the next primary and secondary fires. self:TakePrimaryAmmo(1) -- removes 1 ammo from our clip end -- end our function
Yeah? The comments show everything.
Also, the same thing with the eyetrace, you could have called "bullet" "turkey". So instead of that, you could have put this instead:
local turkey = {} turkey.Num = self.NumBul turkey.Src = self.Owner:GetShootPos() turkey.Dir = self.Owner:GetAimVector() turkey.Spread = Vector( self.Spread, self.Spread, 0 ) turkey.Tracer = 0 turkey.Force = self.Force turkey.Damage = self.Damage turkey.AmmoType = self.Primary.Ammo
I wouldn't, though, because your code will get more and more complicated, when you get better, as "turkey" isn't really a good description of a bullet. However, you could name it "bullet1", then make a completely different bullet that would shoot a different bullet that did different things, and call it "bullet2". You could even try and make it to whereever you hit, the person you hit would jump up and down saying "OMG NO" in chat every second, and then explode. But let's not get into that right now.
Reload
We need to send the animation for reloading when we press 'R'.
function SWEP:Reload() self:DefaultReload( ACT_VM_RELOAD ) -- animation for reloading end
We're done!
Yay! We're done! Just remember to save all of the files, and it should pop up in the weapons menu!
Here's our completed code:
cl_init.lua
include ("shared.lua"); SWEP.PrintName = "My EXPLODING gun!"; SWEP.Slot = 2; SWEP.SlotPos = 4; SWEP.DrawAmmo = true; SWEP.DrawCrosshair = true;
init.lua
AddCSLuaFile ("cl_init.lua"); AddCSLuaFile ("shared.lua"); include ("shared.lua"); SWEP.Weight = 5; SWEP.AutoSwitchTo = false; SWEP.AutoSwitchFrom = false;
SWEP.Author = "cheesylard" SWEP.Contact = "[email protected]" SWEP.Purpose = "Blow up people, duh!" SWEP.Instructions = "Primary to fire a bullet, Secondary to make an explosion where you are pointing" SWEP.Category = "Explosion SWeps" SWEP.Spawnable = false; SWEP.AdminSpawnable = true; SWEP.ViewModel = "models/weapons/v_357.mdl"; SWEP.WorldModel = "models/weapons/w_357.mdl"; SWEP.Primary.ClipSize = 8; SWEP.Primary.DefaultClip = 20; SWEP.Primary.Automatic = false; SWEP.Primary.Ammo = "357"; SWEP.Secondary.ClipSize = -1; SWEP.Secondary.DefaultClip = -1; SWEP.Secondary.Automatic = false; SWEP.Secondary.Ammo = "none"; SWEP.Sound = Sound ("weapon_357.Single") SWEP.Damage = 50 SWEP.Spread = 0.02 SWEP.NumBul = 1 SWEP.Delay = 0.6 SWEP.Force = 3 function SWEP:Deploy() return true end function SWEP:Holster() return true end function SWEP:Think() end -- I made a single line comment! /* I made a multi line comment! OMG, another line! And another! */ --[[ I made another multi-line comment! AND ANOTHER LINE! and another! etc ]] function SWEP:SecondaryAttack() -- when secondary attack happens -- Make sure we can shoot first if ( !self:CanPrimaryAttack() ) then return end local eyetrace = self.Owner:GetEyeTrace(); -- this gets where you are looking. The SWep is making an explosion where you are LOOKING, right? self:EmitSound ( self.Sound ) -- this makes the sound, which I specified earlier in the code self:SendWeaponAnim( ACT_VM_PRIMARYATTACK ) -- this makes the shooting animation for the 357 local explode = ents.Create( "env_explosion" ) -- creates the explosion explode:SetPos( eyetrace.HitPos ) -- this creates the explosion where you were looking explode:SetOwner( self.Owner ) -- this sets you as the person who made the explosion explode:Spawn() -- this actually spawns the explosion explode:SetKeyValue( "iMagnitude", "220" ) -- the magnitude explode:Fire( "Explode", 0, 0 ) explode:EmitSound( "weapon_AWP.Single", 400, 400 ) -- the sound for the explosion, and how far away it can be heard self:SetNextPrimaryFire( CurTime() + self.Delay ) self:SetNextSecondaryFire( CurTime() + self.Delay ) -- this sets the delay for the next primary and secondary fires. self:TakePrimaryAmmo(1) -- removes 1 ammo from our clip end -- telling Gmod that it's the end of the function function SWEP:PrimaryAttack() -- when +attack1 happens -- Make sure we can shoot first if ( !self:CanPrimaryAttack() ) then return end local bullet = {} -- creates a table for the properties of the bullet bullet.Num = self.NumBul -- number of bullets you are shooting bullet.Src = self.Owner:GetShootPos() -- Source, where you are standing bullet.Dir = self.Owner:GetAimVector() -- direction of bullet, where you are looking bullet.Spread = Vector( self.Spread, self.Spread, 0 ) -- spread of bullet, how accurate it is bullet.Tracer = 0 -- this doesn't really affect anything bullet.Force = self.Force -- how powerful it is bullet.Damage = self.Damage -- how much damage it does to people bullet.AmmoType = self.Primary.Ammo -- what type of ammo you are using self.Owner:FireBullets( bullet ) --actually shoots the bullet. self:EmitSound ( self.Sound ) -- this makes the sound, which I specified earlier in the code self:SendWeaponAnim( ACT_VM_PRIMARYATTACK ) -- this makes the shooting animation for the 357 self:SetNextPrimaryFire( CurTime() + self.Delay ) self:SetNextSecondaryFire( CurTime() + self.Delay ) -- this sets the delay for the next primary and secondary fires. self:TakePrimaryAmmo(1) -- removes 1 ammo from our clip end -- end our function function SWEP:Reload() self:DefaultReload( ACT_VM_RELOAD ) -- animation for reloading end
Also, feel free to edit this as you wish. This is why this was created. =)