wiremod-svn-archive/wire/lua/weapons/gmod_tool/stools/wire_explosive.lua
2007-02-04 07:18:10 +00:00

351 lines
14 KiB
Lua

TOOL.Category = "Wire - Physics"
TOOL.Name = "Explosives"
TOOL.Command = nil
TOOL.ConfigName = nil
TOOL.ClientConVar[ "model" ] = "models/props_c17/oildrum001_explosive.mdl"
TOOL.ClientConVar[ "modelman" ] = ""
TOOL.ClientConVar[ "usemodelman" ] = 0
TOOL.ClientConVar[ "effect" ] = "Explosion"
TOOL.ClientConVar[ "tirgger" ] = 1 // Current tirgger
TOOL.ClientConVar[ "damage" ] = 200 // Damage to inflict
TOOL.ClientConVar[ "doblastdamage" ] = 1
TOOL.ClientConVar[ "radius" ] = 300
TOOL.ClientConVar[ "removeafter" ] = 0
TOOL.ClientConVar[ "affectother" ] = 0
TOOL.ClientConVar[ "notaffected" ] = 0
TOOL.ClientConVar[ "delaytime" ] = 0
TOOL.ClientConVar[ "delayreloadtime" ] = 0
TOOL.ClientConVar[ "freeze" ] = 0
TOOL.ClientConVar[ "weld" ] = 1
TOOL.ClientConVar[ "maxhealth" ] = 100
TOOL.ClientConVar[ "bulletproof" ] = 0
TOOL.ClientConVar[ "explosionproof" ] = 0
TOOL.ClientConVar[ "weight" ] = 400
TOOL.ClientConVar[ "explodeatzero" ] = 1
TOOL.ClientConVar[ "resetatexplode" ] = 1
TOOL.ClientConVar[ "fireeffect" ] = 1
TOOL.ClientConVar[ "coloreffect" ] = 1
TOOL.ClientConVar[ "nocollide" ] = 0
TOOL.ClientConVar[ "noparentremove" ] = 0
TOOL.ClientConVar[ "invisibleatzero" ] = 0
cleanup.Register( "wire_explosive" )
if ( CLIENT ) then
language.Add( "Tool_wire_explosive_name", "Wired Explosives Tool" )
language.Add( "Tool_wire_explosive_desc", "Creates a variety of different explosives for wire system." )
language.Add( "Tool_wire_explosive_0", "Left click to place the bomb. Right click update." )
language.Add( "WireExplosiveTool_Model", "Model:" )
language.Add( "WireExplosiveTool_modelman", "Manual model selection:" )
language.Add( "WireExplosiveTool_usemodelman", "Use manual model selection:" )
language.Add( "WireExplosiveTool_Effects", "Effect:" )
language.Add( "WireExplosiveTool_tirgger", "Trigger value:" )
language.Add( "WireExplosiveTool_damage", "Dammage:" )
language.Add( "WireExplosiveTool_delay", "On fire time (delay after triggered before explosion):" )
language.Add( "WireExplosiveTool_delayreload", "Delay after explosion before it can be triggered again:" )
language.Add( "WireExplosiveTool_remove", "Remove on explosion:" )
language.Add( "WireExplosiveTool_doblastdamage", "Do blast damage:" )
language.Add( "WireExplosiveTool_affectother", "Dammaged/moved by other wired explosives:" )
language.Add( "WireExplosiveTool_notaffected", "Not moved by any phyiscal damage:" )
language.Add( "WireExplosiveTool_radius", "Blast radius:" )
language.Add( "WireExplosiveTool_freeze", "Freeze:" )
language.Add( "WireExplosiveTool_weld", "Weld:" )
language.Add( "WireExplosiveTool_noparentremove", "Don't remove on parent remove:" )
language.Add( "WireExplosiveTool_nocollide", "No collide all but world:" )
language.Add( "WireExplosiveTool_maxhealth", "Max health:" )
language.Add( "WireExplosiveTool_weight", "Weight:" )
language.Add( "WireExplosiveTool_bulletproof", "Bullet proof:" )
language.Add( "WireExplosiveTool_explosionproof", "Explosion proof:" )
language.Add( "WireExplosiveTool_fallproof", "Fall proof:" )
language.Add( "WireExplosiveTool_explodeatzero", "Explode when health = zero:" )
language.Add( "WireExplosiveTool_resetatexplode", "Rest health then:" )
language.Add( "WireExplosiveTool_fireeffect", "Enable fire effect on triggered:" )
language.Add( "WireExplosiveTool_coloreffect", "Enable color change effect on damage:" )
language.Add( "WireExplosiveTool_invisibleatzero", "Become invisible when health reaches 0:" )
language.Add( "Undone_WireExplosive", "Wired Explosive undone" )
language.Add( "sbox_maxwire_explosive", "You've hit wired explosives limit!" )
end
if (SERVER) then
CreateConVar('sbox_maxwire_explosive', 30)
end
function TOOL:LeftClick( trace )
if (!trace.HitPos) then return false end
if (trace.Entity:IsPlayer()) then return false end
if ( CLIENT ) then return true end
local ply = self:GetOwner()
if ( !self:GetSWEP():CheckLimit( "wire_explosive" ) ) then return false end
// Get client's CVars
local _tirgger = self:GetClientNumber( "tirgger" )
local _damage = math.Clamp( self:GetClientNumber( "damage" ), 0, 1500 )
local _removeafter = self:GetClientNumber( "removeafter" ) == 1
local _delaytime = self:GetClientNumber( "delaytime" )
local _delayreloadtime = self:GetClientNumber( "delayreloadtime" )
local _doblastdamage = self:GetClientNumber( "doblastdamage" ) == 1
local _radius = self:GetClientNumber( "radius" )
local _affectother = self:GetClientNumber( "affectother" ) == 1
local _notaffected = self:GetClientNumber( "notaffected" ) == 1
local _freeze = self:GetClientNumber( "freeze" ) == 1
local _weld = self:GetClientNumber( "weld" ) == 1
local _maxhealth = self:GetClientNumber( "maxhealth" )
local _bulletproof = self:GetClientNumber( "bulletproof" ) == 1
local _explosionproof = self:GetClientNumber( "explosionproof" ) == 1
local _fallproof = self:GetClientNumber( "fallproof" ) == 1
local _explodeatzero = self:GetClientNumber( "explodeatzero" ) == 1
local _resetatexplode = self:GetClientNumber( "resetatexplode" ) == 1
local _fireeffect = self:GetClientNumber( "fireeffect" ) == 1
local _coloreffect = self:GetClientNumber( "coloreffect" ) == 1
local _noparentremove = self:GetClientNumber( "noparentremove" ) == 1
local _nocollide = self:GetClientNumber( "nocollide" ) == 1
local _weight = self:GetClientNumber( "weight" )
local _invisibleatzero = self:GetClientNumber( "invisibleatzero" ) == 1
//get & check selected model
_model = self:GetSelModel( true )
if (!_model) then return false end
local Ang = trace.HitNormal:Angle()
Ang.pitch = Ang.pitch + 90
local explosive = MakeWireExplosive( ply, trace.HitPos, Ang, _tirgger, _damage, _model, _removeafter, _delaytime, _doblastdamage, _radius, _affectother, _notaffected, _delayreloadtime, _maxhealth, _bulletproof, _explosionproof, _fallproof, _explodeatzero, _resetatexplode, _fireeffect, _coloreffect, _invisibleatzero, _nocollide )
local min = explosive:OBBMins()
explosive:SetPos( trace.HitPos - trace.HitNormal * min.z )
if ( _freeze ) then
explosive:GetPhysicsObject():Sleep() //will freeze the explosive till something touches it
end
// Don't weld to world
if ( trace.Entity:IsValid() && _weld ) then
const, nocollide = constraint.Weld( explosive, trace.Entity, 0, trace.PhysicsBone, 0, collision == 0 )
if (!_noparentremove) then trace.Entity:DeleteOnRemove( explosive ) end
end
if (_weight <= 0) then _weight = 1 end
explosive.Entity:GetPhysicsObject():SetMass(_weight)
undo.Create("WireExplosive")
undo.AddEntity( explosive )
undo.SetPlayer( ply )
undo.Finish()
ply:AddCleanup( "wire_explosive", explosive )
return true
end
function TOOL:GetSelModel( showerr )
local model = self:GetClientInfo( "model" )
if (model == "usemanmodel") then
local _modelman = self:GetClientInfo( "modelman" )
if (_modelman && string.len(_modelman) > 0) then
model = _modelman
else
local message = "You need to define a model."
if (showerr) then
self:GetOwner():PrintMessage(3, message)
self:GetOwner():PrintMessage(2, message)
end
return false
end
elseif (model == "usereloadmodel") then
if (self.reloadmodel && string.len(self.reloadmodel) > 0) then
model = self.reloadmodel
else
local message = "You need to select a model model."
if (showerr) then
self:GetOwner():PrintMessage(3, message)
self:GetOwner():PrintMessage(2, message)
end
return false
end
end
if (not util.IsValidModel(model)) then
//something fucked up, notify user of that
local message = "This is not a valid model."..model
if (showerr) then
self:GetOwner():PrintMessage(3, message)
self:GetOwner():PrintMessage(2, message)
end
return false
end
if (not util.IsValidProp(model)) then return false end
return model
end
function TOOL:RightClick( trace )
local ply = self:GetOwner()
//shot an explosive, update it instead
if ( trace.Entity:IsValid() && trace.Entity:GetClass() == "gmod_wire_explosive" && trace.Entity:GetTable().pl == ply ) then
//double you code double your fun (copy from above)
// Get client's CVars
local _tirgger = self:GetClientNumber( "tirgger" )
local _damage = math.Clamp( self:GetClientNumber( "damage" ), 0, 1500 )
local _removeafter = self:GetClientNumber( "removeafter" ) == 1
local _delaytime = self:GetClientNumber( "delaytime" )
local _delayreloadtime = self:GetClientNumber( "delayreloadtime" )
local _doblastdamage = self:GetClientNumber( "doblastdamage" ) == 1
local _radius = self:GetClientNumber( "radius" )
local _affectother = self:GetClientNumber( "affectother" ) == 1
local _notaffected = self:GetClientNumber( "notaffected" ) == 1
local _freeze = self:GetClientNumber( "freeze" ) == 1
local _weld = self:GetClientNumber( "weld" ) == 1
local _maxhealth = self:GetClientNumber( "maxhealth" )
local _bulletproof = self:GetClientNumber( "bulletproof" ) == 1
local _explosionproof = self:GetClientNumber( "explosionproof" ) == 1
local _fallproof = self:GetClientNumber( "fallproof" ) == 1
local _explodeatzero = self:GetClientNumber( "explodeatzero" ) == 1
local _resetatexplode = self:GetClientNumber( "resetatexplode" ) == 1
local _fireeffect = self:GetClientNumber( "fireeffect" ) == 1
local _coloreffect = self:GetClientNumber( "coloreffect" ) == 1
local _noparentremove = self:GetClientNumber( "noparentremove" ) == 1
local _nocollide = self:GetClientNumber( "nocollide" ) == 1
local _weight = self:GetClientNumber( "weight" )
local _invisibleatzero = self:GetClientNumber( "invisibleatzero" ) == 1
trace.Entity:GetTable():Setup( _damage, _delaytime, _removeafter, _doblastdamage, _radius, _affectother, _notaffected, _delayreloadtime, _maxhealth, _bulletproof, _explosionproof, _fallproof, _explodeatzero, _resetatexplode, _fireeffect, _coloreffect, _invisibleatzero, _nocollide )
if (_weight <= 0) then _weight = 1 end
trace.Entity:GetPhysicsObject():SetMass(_weight)
//reset color in case we turned the color effect off and it's still red
trace.Entity:SetColor(255, 255, 255, 255)
return true
end
end
function TOOL:Reload( trace )
//get the model of what was shot and set our reloadmodel to that
//model info getting code mostly copied from OverloadUT's What Is That? STool
if !trace.Entity then return false end
local ent = trace.Entity
local ply = self:GetOwner()
local class = ent:GetClass()
if class == "worldspawn" then
return false
else
local model = ent:GetModel()
local message = "Model selected: "..model
self.reloadmodel = model
ply:PrintMessage(3, message)
ply:PrintMessage(2, message)
end
return true
end
if SERVER then
function MakeWireExplosive(pl, Pos, Ang, key, damage, model, removeafter, delaytime, doblastdamage, radius, affectother, notaffected, delayreloadtime, maxhealth, bulletproof, explosionproof, fallproof, explodeatzero, resetatexplode, fireeffect, coloreffect, invisibleatzero, nocollide, Vel, aVel, frozen )
if ( !pl:CheckLimit( "wire_explosive" ) ) then return nil end
local explosive = ents.Create( "gmod_wire_explosive" )
explosive:SetModel( model )
explosive:SetPos( Pos )
explosive:SetAngles( Ang )
explosive:Spawn()
explosive:Activate()
explosive:GetTable():Setup( damage, delaytime, removeafter, doblastdamage, radius, affectother, notaffected, delayreloadtime, maxhealth, bulletproof, explosionproof, fallproof, explodeatzero, resetatexplode, fireeffect, coloreffect, invisibleatzero, nocollide )
explosive:GetTable():SetPlayer( pl )
local ttable =
{
key = key,
pl = pl,
nocollide = nocollide,
description = description,
key = key,
damage = damage,
model = model,
removeafter = removeafter,
delaytime = delaytime,
doblastdamage = doblastdamage,
radius = radius,
affectother = affectother,
notaffected = notaffected,
delayreloadtime = delayreloadtime,
maxhealth = maxhealth,
bulletproof = bulletproof,
explosionproof = explosionproof,
fallproof = fallproof,
explodeatzero = explodeatzero,
resetatexplode = resetatexplode,
fireeffect = fireeffect,
coloreffect = coloreffect,
invisibleatzero = invisibleatzero
}
table.Merge( explosive:GetTable(), ttable )
pl:AddCount( "wire_explosive", explosive )
return explosive
end
duplicator.RegisterEntityClass( "gmod_wire_explosive", MakeWireExplosive, "Pos", "Ang", "key", "damage", "model", "removeafter", "delaytime", "doblastdamage", "radius", "affectother", "notaffected", "delayreloadtime", "maxhealth", "bulletproof", "explosionproof", "fallproof", "explodeatzero", "resetatexplode", "fireeffect", "coloreffect", "invisibleatzero", "nocollide", "Vel", "aVel", "frozen" )
end
function TOOL:UpdateGhostWireExplosive( ent, player )
if ( !ent || !ent:IsValid() ) then return end
local tr = utilx.GetPlayerTrace( player, player:GetCursorAimVector() )
local trace = util.TraceLine( tr )
if (!trace.Hit || trace.Entity:IsPlayer() ) then -- || trace.Entity:GetClass() == "gmod_wire_explosive"
ent:SetNoDraw( true )
return
end
local Ang = trace.HitNormal:Angle()
Ang.pitch = Ang.pitch + 90
local min = ent:OBBMins()
ent:SetPos( trace.HitPos - trace.HitNormal * min.z )
ent:SetAngles( Ang )
ent:SetNoDraw( false )
end
function TOOL:Think()
if (!self.GhostEntity || !self.GhostEntity:IsValid() || self.GhostEntity:GetModel() != self:GetSelModel()) then
local _model = self:GetSelModel()
if (!_model) then return end
self:MakeGhostEntity( _model, Vector(0,0,0), Angle(0,0,0) )
end
self:UpdateGhostWireExplosive( self.GhostEntity, self:GetOwner() )
end