new Inventory system

This commit is contained in:
Fesiug 2024-10-08 20:46:36 -04:00
parent 825c32e217
commit 3975ebf158
Signed by: Fesiug
GPG Key ID: 374BFF45E1EEF243
10 changed files with 517 additions and 267 deletions

View File

@ -0,0 +1,159 @@
AddCSLuaFile()
ENT.Type = "point"
function ENT:SetupDataTables()
for i=1, 32 do
self:NetworkVar("Entity", i-1, "Item" .. i )
end
self:NetworkVar( "Int", "ReservedSlots" )
end
function ENT:Initialize()
self:AddEFlags( EFL_FORCE_CHECK_TRANSMIT )
self:SetTransmitWithParent( true ) -- Transmit only when the owner does
end
function ENT:Think()
if !self:GetOwner():IsValid() then
self:Print("existing without an owner." )
end
end
function ENT:Print( ... )
print( "[Inventory[" .. self:EntIndex() .. "], " .. tostring(self:GetOwner()) .. "]", ...)
end
function ENT:UpdateTransmitState()
return TRANSMIT_ALWAYS
end
function ENT:ReevalRecreate()
self:RemoveEFlags( EFL_KEEP_ON_RECREATE_ENTITIES )
if self:GetOwner():IsValid() then
if self:GetOwner():IsEFlagSet( EFL_KEEP_ON_RECREATE_ENTITIES ) then
self:AddEFlags( EFL_KEEP_ON_RECREATE_ENTITIES )
self:Print("To be saved during recreate.")
return
else
self:Print("Will NOT be saved during recreate.")
return
end
end
self:Print("Will NOT be saved during recreate. No owner either")
return
end
function ENT:AttachToEntity( ent )
if ent.SetInventory then
ent:SetInventory( self )
else
error( "[Inventory " .. tostring(self) .. "] " .. tostring(ent) .. " doesn't have a SetInventory function. Not attaching.")
return
end
self:SetOwner( ent )
self:SetParent( ent )
self:SetPos( vector_origin )
self:SetAngles( angle_zero )
self:ReevalRecreate()
self:Print("Attached to: " .. tostring(ent))
end
function ENT:GetItems()
local itemlist = {}
for i=1, 32 do
local curr = self["GetItem"..i](self)
if curr == NULL then continue end
table.insert( itemlist, curr )
end
return itemlist
end
function ENT:GetWeighted()
local itemlist = {}
for i, v in pairs(self:GetItems()) do
if i == 0 then continue end
table.insert( itemlist, v )
end
table.sort( itemlist, function( a, b )
return a:GetAcquisition() < b:GetAcquisition()
end)
return itemlist
end
function ENT:AddItem( ent )
if !ent:IsValid() then
self:Print("Invalid entity, printing trace" )
debug.Trace()
return false
end
for i=1+self:GetReservedSlots(), 32 do
local curr = self["GetItem"..i](self)
if curr == NULL then continue end
if curr == ent then self:Print("We already own this entity " .. tostring(ent) ) return false end
end
for i=1+self:GetReservedSlots(), 32 do
local curr = self["GetItem"..i](self)
if curr == NULL then
self["SetItem"..i](self, ent)
ent:SetParent( self:GetOwner() )
ent:SetOwner( self:GetOwner() )
self:ReevalRecreate() -- Why do I have to do this.
if ent.GetInventory then ent:GetInventory():ReevalRecreate() end
return true
end
end
self:Print("Inventory full, can't fit " .. tostring(ent) )
return false
end
function ENT:RemoveItem( ent )
if !ent:IsValid() then
self:Print("Invalid entity, printing trace" )
debug.Trace()
return false
end
for i=1+self:GetReservedSlots(), 32 do
local curr = self["GetItem"..i](self)
if curr == ent then
self["SetItem"..i](self, NULL)
ent:SetParent( NULL )
ent:SetOwner( NULL )
self:ReevalRecreate() -- Why do I have to do this.
if ent.GetInventory then ent:GetInventory():ReevalRecreate() end
return true
end
end
self:Print("Couldn't remove " .. tostring(ent) .. " from inventory." )
return false
end
function ENT:GetItem( ent )
if !ent:IsValid() then
self:Print("Invalid entity, printing trace" )
debug.Trace()
return false
end
for i=1+self:GetReservedSlots(), 32 do
local curr = self["GetItem"..i](self)
if curr == ent then
return curr, i
end
end
self:Print("Couldn't find " .. tostring(ent) .. " in inventory." )
return false
end

View File

@ -62,11 +62,14 @@ end
function SWEP:SetActive( ent ) function SWEP:SetActive( ent )
local p = self:GetOwner() local p = self:GetOwner()
if ent:GetOwner() != p then return false end if ent:GetOwner() != p then return false end
--if self:GetActiveR():IsValid() then self:Deactive() end
self:SetActiveR( ent ) self:SetActiveR( ent )
if self:GetActiveR():IsValid() then if ent:IsValid() then
self:GetActiveR():Deploy() ent:Deploy()
self:GetActiveR():SetNoDraw( false ) ent:SetNoDraw( false )
-- LAZY FIX
for i, v in ipairs(ent:GetChildren()) do
v:SetNoDraw(false)
end
end end
return true return true
end end
@ -75,7 +78,6 @@ function SWEP:Deactive()
end end
function SWEP:PrimaryAttack() function SWEP:PrimaryAttack()
local p = self:GetOwner()
if self:GetActiveR():IsValid() then if self:GetActiveR():IsValid() then
self:GetActiveR():Attack() self:GetActiveR():Attack()
end end
@ -88,7 +90,6 @@ function SWEP:Reload()
end end
function SWEP:SecondaryAttack() function SWEP:SecondaryAttack()
local p = self:GetOwner()
if self:GetActiveR():IsValid() then if self:GetActiveR():IsValid() then
self:GetActiveR():AttackAlt() self:GetActiveR():AttackAlt()
end end
@ -121,27 +122,34 @@ function SWEP:EquipItem( ent )
end end
print("[equip]", ent) print("[equip]", ent)
self:SetDesireR( ent ) --self:SetDesireR( ent )
ent:SetHandler( self )
ent:AddEFlags( EFL_KEEP_ON_RECREATE_ENTITIES ) ent:AddEFlags( EFL_KEEP_ON_RECREATE_ENTITIES )
ent:AddEffects( EF_BONEMERGE + EF_BONEMERGE_FASTCULL ) ent:AddEffects( EF_BONEMERGE + EF_BONEMERGE_FASTCULL + EF_NOINTERP )
ent:PhysicsInit( SOLID_NONE ) ent:PhysicsInit( SOLID_NONE )
ent:SetMoveType( MOVETYPE_NONE ) ent:SetMoveType( MOVETYPE_NONE )
ent:SetAcquisition( CurTime() )
-- Inventory
local inv = p:GetInventory()
local result = inv:AddItem( ent )
if !result then
print("[EquipItem " .. tostring(self) .. "] AddItem failed! " .. tostring(ent))
return
end
ent:SetNoDraw( true ) ent:SetNoDraw( true )
ent:SetParent( p ) -- LAZY FIX
ent:SetOwner( p ) for i, v in ipairs(ent:GetChildren()) do
ent:SetHandler( self ) v:SetNoDraw(true)
end
ent:SetLocalPos( vector_origin ) ent:SetLocalPos( vector_origin )
ent:SetLocalAngles( angle_zero ) ent:SetLocalAngles( angle_zero )
ent:SetAcquisition( CurTime() )
ent:EmitSound( "ae/items/pickup.ogg", 70, 100, 1, CHAN_STATIC ) ent:EmitSound( "ae/items/pickup.ogg", 70, 100, 1, CHAN_STATIC )
--self:SetActive( ent ) -- Start prediction
local inv = p:GetInventory()
inv[ent] = true
inv:Sync()
net.Start("AEINV_PredictItem") net.Start("AEINV_PredictItem")
net.WriteEntity( ent ) net.WriteEntity( ent )
net.WriteBool( true ) net.WriteBool( true )
@ -156,9 +164,6 @@ function SWEP:DropItem()
if CLIENT then print("[drop] DropItem called on cl not allowed") return end if CLIENT then print("[drop] DropItem called on cl not allowed") return end
self:SetDesireR( NULL ) self:SetDesireR( NULL )
ent:SetParent( NULL )
ent:SetOwner( NULL )
ent:SetHandler( NULL ) ent:SetHandler( NULL )
ent:RemoveEFlags( EFL_KEEP_ON_RECREATE_ENTITIES ) ent:RemoveEFlags( EFL_KEEP_ON_RECREATE_ENTITIES )
@ -166,15 +171,22 @@ function SWEP:DropItem()
ent:PhysicsInit( SOLID_VPHYSICS ) ent:PhysicsInit( SOLID_VPHYSICS )
ent:SetMoveType( MOVETYPE_VPHYSICS ) ent:SetMoveType( MOVETYPE_VPHYSICS )
ent:SetCollisionGroup( COLLISION_GROUP_PROJECTILE ) ent:SetCollisionGroup( COLLISION_GROUP_PROJECTILE )
ent:SetNoDraw( false )
-- Inventory
local inv = p:GetInventory()
local result = inv:RemoveItem( ent )
if !result then
print("[DropItem " .. tostring(self) .. "] RemoveItem failed! " .. tostring(ent))
return
end
ent:SetNoDraw( false )
-- LAZY FIX
for i, v in ipairs(ent:GetChildren()) do
v:SetNoDraw(false)
end
ent:SetPos( p:EyePos() + p:GetAimVector() * 0 ) ent:SetPos( p:EyePos() + p:GetAimVector() * 0 )
ent:SetAngles( p:EyeAngles() + Angle( 0, 180, 0 ) ) ent:SetAngles( p:EyeAngles() + Angle( 0, 180, 0 ) )
local inv = p:GetInventory()
inv[ent] = nil
inv:Sync()
local ep = ent:GetPhysicsObject() local ep = ent:GetPhysicsObject()
ep:SetVelocity( p:GetAimVector() * 800 ) ep:SetVelocity( p:GetAimVector() * 800 )

View File

@ -368,6 +368,6 @@ function printallbones( ent )
end end
end end
concommand.Add("b-debug_listbones", function( ply, cmd ) concommand.Add("b-debug_listbones", function( ply, cmd, args )
printallbones( ply ) printallbones( args[1] and Entity(args[1]) or ply )
end) end)

View File

@ -369,77 +369,81 @@ function GM:HUDPaint()
S_Pop() S_Pop()
if handler then if handler then
-- Inventory if !p:GetInventory():IsValid() then
local Pw, Ph, Pg = 110, 30, 10 hTextS( "No inventory entity!!", "HUD_36", ScrW()/2, ScrH() - 20 - 36, COLOR_MAIN, TEXT_ALIGN_CENTER, nil, COLOR_DARK )
local thespace = 0 else
for i, v in ipairs( p:GetInventory():GetWeighted() ) do -- Inventory
thespace = thespace + Pw + Pg local Pw, Ph, Pg = 110, 30, 10
end local thespace = 0
thespace = thespace - Pg
thespace = thespace/2
S_Push( ScrW()/2 - thespace, ScrH() - 20 - Ph )
for i, v in ipairs( p:GetInventory():GetWeighted() ) do for i, v in ipairs( p:GetInventory():GetWeighted() ) do
hCol( v == handler:GetDesireR() and COLOR_BRIGHT or COLOR_DARK ) thespace = thespace + Pw + Pg
hRect( (i-1)*(Pw+Pg), 0, Pw, Ph )
if v == handler:GetActiveR() then
hCol( COLOR_MAIN )
hORect( (i-1)*(Pw+Pg)+1, 1, Pw-2, Ph-2, 1 )
end
local x, y = (i-1)*(Pw+Pg), 0
hText( l8( v.Class.PrintName ), "HUD_24", x + Pw/2, y + 5, COLOR_MAIN, TEXT_ALIGN_CENTER )
hText( i, "HUD_16", x + 4, y + 2, COLOR_MAIN )
end end
S_Pop() thespace = thespace - Pg
thespace = thespace/2
local wep = handler:GetDesireR() S_Push( ScrW()/2 - thespace, ScrH() - 20 - Ph )
if wep and wep.GetClip then for i, v in ipairs( p:GetInventory():GetWeighted() ) do
local Bw, Bh = 8+(8+2)*30-2+8, 160 hCol( v == handler:GetDesireR() and COLOR_BRIGHT or COLOR_DARK )
S_Push( w - 20 - Bw, h - 20 - Bh ) hRect( (i-1)*(Pw+Pg), 0, Pw, Ph )
hCol( COLOR_DARK ) if v == handler:GetActiveR() then
hRect( 0, 0, Bw, Bh ) hCol( COLOR_MAIN )
hORect( (i-1)*(Pw+Pg)+1, 1, Pw-2, Ph-2, 1 )
S_Push( 0, 0 ) end
hCol( COLOR_MAIN ) local x, y = (i-1)*(Pw+Pg), 0
local leng = Bw-8-8 hText( l8( v.Class.PrintName ), "HUD_24", x + Pw/2, y + 5, COLOR_MAIN, TEXT_ALIGN_CENTER )
hRect( 8, 8, leng-70, 26 ) hText( i, "HUD_16", x + 4, y + 2, COLOR_MAIN )
hRect( 8 + leng - 70 + 4, 8, leng-(leng-70)-4, 26 )
hText( l8( wep.Class.PrintName ), "HUD_36", 12, 6, COLOR_DARK )
local bc = wep.Class.BurstCount
hText( fmlookup[bc] or bc .. "RND", "HUD_24", 10 + (leng - 70) + 70/2, 11, COLOR_DARK, TEXT_ALIGN_CENTER )
S_Pop()
local Tw, Th = 6, 18
if wep.Class.ClipSize>45 then
Tw = 3
Th = 13
elseif wep.Class.ClipSize<14 then
Tw = 8
Th = 22
end end
S_Push( Bw - Tw - 8, Bh - Th - 8 )
for i=0, wep.Class.ClipSize-1 do
if i>29 then
hCol( COLOR_DARK )
hRect( (0 - Tw - 2)*i-4, -4, Tw+2, Th+8 )
end
end
for i=0, wep.Class.ClipSize-1 do
if wep:GetClip() >= (i+1) then
hCol( COLOR_MAIN )
hRect( (0 - Tw - 2)*i, 0, Tw, Th )
hCol( COLOR_DARK )
hRect( (0 - Tw - 2)*i, Th-4, Tw, 2 )
else
hCol( COLOR_BRIGHT )
hORect( (0 - Tw - 2)*i, 0, Tw, Th )
--hORect( (0 - 8 - 2)*i+1, 1, 8-2, 18-2 )
end
end
S_Pop()
S_Pop() S_Pop()
local wep = handler:GetDesireR()
if wep and wep.GetClip then
local Bw, Bh = 8+(8+2)*30-2+8, 160
S_Push( w - 20 - Bw, h - 20 - Bh )
hCol( COLOR_DARK )
hRect( 0, 0, Bw, Bh )
S_Push( 0, 0 )
hCol( COLOR_MAIN )
local leng = Bw-8-8
hRect( 8, 8, leng-70, 26 )
hRect( 8 + leng - 70 + 4, 8, leng-(leng-70)-4, 26 )
hText( l8( wep.Class.PrintName ), "HUD_36", 12, 6, COLOR_DARK )
local bc = wep.Class.BurstCount
hText( fmlookup[bc] or bc .. "RND", "HUD_24", 10 + (leng - 70) + 70/2, 11, COLOR_DARK, TEXT_ALIGN_CENTER )
S_Pop()
local Tw, Th = 6, 18
if wep.Class.ClipSize>45 then
Tw = 3
Th = 13
elseif wep.Class.ClipSize<14 then
Tw = 8
Th = 22
end
S_Push( Bw - Tw - 8, Bh - Th - 8 )
for i=0, wep.Class.ClipSize-1 do
if i>29 then
hCol( COLOR_DARK )
hRect( (0 - Tw - 2)*i-4, -4, Tw+2, Th+8 )
end
end
for i=0, wep.Class.ClipSize-1 do
if wep:GetClip() >= (i+1) then
hCol( COLOR_MAIN )
hRect( (0 - Tw - 2)*i, 0, Tw, Th )
hCol( COLOR_DARK )
hRect( (0 - Tw - 2)*i, Th-4, Tw, 2 )
else
hCol( COLOR_BRIGHT )
hORect( (0 - Tw - 2)*i, 0, Tw, Th )
--hORect( (0 - 8 - 2)*i+1, 1, 8-2, 18-2 )
end
end
S_Pop()
S_Pop()
end
end end
end end
@ -873,6 +877,82 @@ local function QuickDrawStat( wide, data, first )
return gap return gap
end end
local c_swag = HSVToColor( 120, 0.5, 1 )
local c_swag2 = HSVToColor( 60, 0.5, 1 )
local c_swag3 = HSVToColor( 180, 0.5, 1 )
local function recurse( ent, y )
local p = LocalPlayer()
local h = p:HandlerCheck()
local inv = ent:GetInventory()
local irs = inv:GetReservedSlots()
S_Push( 20, 0 )
hTextS( "Inventory [" .. inv:EntIndex() .. "]", "HUD_16", 0, y, nil, nil, nil, color_black )
y = y + 12
for i=1, 32 do
local curr = inv["GetItem"..i](self)
if irs < i and curr == NULL then continue end
local ofinterest = curr != NULL and
((curr == h:GetActiveR() or curr == h:GetActiveL()) and c_swag or
(curr == h:GetDesireR() or curr == h:GetDesireL()) and c_swag2) or
irs >= i and c_swag3 or nil
local entname = curr == NULL and (irs >= i and "Reserved" or "Null") or tostring(curr)
hTextS( i, "HUD_16", 0, y, ofinterest, nil, nil, color_black )
hTextS( entname, "HUD_16", 20, y, ofinterest, nil, nil, color_black )
y = y + 12
if curr.GetInventory then
y = recurse( curr, y )
end
end
S_Pop()
return y
end
hook.Add("HUDPaint", "Benny_HUDPaint_Debug", function()
local p = LocalPlayer()
stack = util.Stack()
local y = 0
S_Push( 20, 120 )
hTextS( p, "HUD_16", 0, y, nil, nil, nil, color_black )
y = y + 12
local h = p:HandlerCheck()
if h then
hTextS( "Handler:", "HUD_16", 20, y, nil, nil, nil, color_black )
y = y + 12
hTextS( "R Active: " .. tostring(h:GetActiveR()), "HUD_16", 40, y, nil, nil, nil, color_black )
y = y + 12
hTextS( "R Desire: " .. tostring(h:GetDesireR()), "HUD_16", 40, y, nil, nil, nil, color_black )
y = y + 12
hTextS( "L Active: " .. tostring(h:GetActiveL()), "HUD_16", 40, y, nil, nil, nil, color_black )
y = y + 12
hTextS( "L Desire: " .. tostring(h:GetDesireL()), "HUD_16", 40, y, nil, nil, nil, color_black )
y = y + 12
end
local x = 20+20
y = recurse( p, y )
if false then
hTextS( "Inventory (Weighted):", "HUD_16", 20, y, nil, nil, nil, color_black )
y = y + 12
for i, v in ipairs(p:GetInventory():GetWeighted()) do
hTextS( i .. ": " .. tostring(v), "HUD_16", 20+20, y, nil, nil, nil, color_black )
y = y + 12
end
end
S_Pop()
if stack:Size() != 0 then print("Stack unfinished.") end
return
end)
local ScoreWide = 600 local ScoreWide = 600
function GM:ScoreboardShow() function GM:ScoreboardShow()
drawscoreboard = true drawscoreboard = true

View File

@ -1,179 +1,64 @@
--------------------- local Emeta = FindMetaTable("Entity")
-- Your Name is Benny
---------------------
local PT = FindMetaTable("Player") local qt2 = {
["slot1"] = 1,
["slot2"] = 2,
["slot3"] = 3,
["slot4"] = 4,
["slot5"] = 5,
["slot6"] = 6,
["slot7"] = 7,
["slot8"] = 8,
["slot9"] = 9,
["slot0"] = 0,
}
local qt = {
["invprev"] = -1,
["invnext"] = 1,
}
function PT:GetItems() hook.Add( "PlayerBindPress", "Benny_PlayerBindPress_Original", function( ply, bind, pressed, code )
return if qt2[bind] then
end local Num = qt2[bind]
if pressed then
local inv = ply:GetInventory():GetWeighted()
local wep = ply:HandlerCheck()
local invf = table.Flip( inv )
InventoryMeta = {} local NumOfActive = 0
NumOfActive = invf[wep:GetDesireR()]
function InventoryMeta:Destroy() if Num == NumOfActive then
local p = self[0].Owner Num = 0
p.Inventory = nil
p:GetInventory()
end
function InventoryMeta:BugCheck()
for i, v in pairs(self) do
if i != 0 and !i:IsValid() then
self[i] = nil
end
end
end
function InventoryMeta:GetWeighted()
local itemlist = {}
for i, v in pairs(self) do
if i == 0 then continue end
table.insert( itemlist, i )
end
table.sort( itemlist, function( a, b )
return a:GetAcquisition() < b:GetAcquisition()
end)
return itemlist
end
function InventoryMeta:Sync()
if SERVER then
net.Start("AEINV_InvSync")
local count = table.Count( self )-1 -- The header is included
net.WriteUInt( count, 8 )
for key, _ in pairs( self ) do
if key == 0 then continue end
net.WriteEntity( key )
end end
net.Send( self[0].Owner ) input.SelectWeapon( ply:GetWeapon("goat_"..Num) )
end
return true
end end
end if qt[bind] then
if pressed then
local Num = 0
InventoryMeta.__index = InventoryMeta local inv = ply:GetInventory():GetWeighted()
local wep = ply:HandlerCheck()
local invf = table.Flip( inv )
local invc = #inv
Num = wep:GetDesireR() and invf[wep:GetDesireR()] or 0
Num = Num + qt[bind]
function PT:GetInventory() if Num > invc then
if !self.Inventory then Num = 0
print("[inventory] new inventory created: ", self) elseif Num < 0 then
self.Inventory = {} Num = invc
self.Inventory[0] = { Owner = self }
setmetatable( self.Inventory, InventoryMeta )
if SERVER then
for i, v in pairs( self:GetChildren() ) do
if v.AEItem then
print( "[inventory] regen: adding", v)
self.Inventory[v] = true
end
end end
self.Inventory:Sync()
input.SelectWeapon( ply:GetWeapon("goat_"..Num) )
end end
return true
end end
end)
self.Inventory:BugCheck()
return self.Inventory
end
gameevent.Listen( "OnRequestFullUpdate" )
hook.Add( "OnRequestFullUpdate", "Benny_OnRequestFullUpdate_Inventory", function( data )
local name = data.name // Same as Player:Nick()
local steamid = data.networkid // Same as Player:SteamID()
local id = data.userid // Same as Player:UserID()
local index = data.index // Same as Entity:EntIndex() minus one
if SERVER then
print("[inventory]", Player(id), "FullUpdate resync")
Player(id):GetInventory():Sync()
end
end )
if SERVER then
util.AddNetworkString("AEINV_InvSync")
else
net.Receive("AEINV_InvSync", function()
print("[inventory] sync start:")
local p = LocalPlayer()
p.Inventory = nil
if p.GetInventory then
local inv = p:GetInventory()
local count = net.ReadUInt(8)
for i=1, count do
local key = net.ReadEntity()
print( "\tadded", key)
inv[key] = true
end
else
print("\ti don't have an inventory, maybe you asked too early!!")
end
print("\tsync done")
end)
end
do
local qt2 = {
["slot1"] = 1,
["slot2"] = 2,
["slot3"] = 3,
["slot4"] = 4,
["slot5"] = 5,
["slot6"] = 6,
["slot7"] = 7,
["slot8"] = 8,
["slot9"] = 9,
["slot0"] = 0,
}
local qt = {
["invprev"] = -1,
["invnext"] = 1,
}
hook.Add( "PlayerBindPress", "Benny_PlayerBindPress_Original", function( ply, bind, pressed, code )
if qt2[bind] then
local Num = qt2[bind]
if pressed then
local inv = ply:GetInventory():GetWeighted()
local wep = ply:HandlerCheck()
local invf = table.Flip( inv )
local NumOfActive = 0
NumOfActive = invf[wep:GetDesireR()]
if Num == NumOfActive then
Num = 0
end
input.SelectWeapon( ply:GetWeapon("goat_"..Num) )
end
return true
end
if qt[bind] then
if pressed then
local Num = 0
local inv = ply:GetInventory():GetWeighted()
local wep = ply:HandlerCheck()
local invf = table.Flip( inv )
local invc = #inv
Num = wep:GetDesireR() and invf[wep:GetDesireR()] or 0
Num = Num + qt[bind]
if Num > invc then
Num = 0
elseif Num < 0 then
Num = invc
end
input.SelectWeapon( ply:GetWeapon("goat_"..Num) )
end
return true
end
end)
end
hook.Add( "PlayerSwitchWeapon", "Benny_PlayerSwitchWeapon_Goat", function( ply, old, ent ) hook.Add( "PlayerSwitchWeapon", "Benny_PlayerSwitchWeapon_Goat", function( ply, old, ent )
if ent.BennyItemHandler then return true end -- what happened? if ent.BennyItemHandler then return true end -- what happened?
@ -195,7 +80,6 @@ end)
for i=0, 9 do for i=0, 9 do
local tent = {} local tent = {}
--tent.Base = "goat"
tent.Goat = i tent.Goat = i
weapons.Register( tent, "goat_" .. i ) weapons.Register( tent, "goat_" .. i )

View File

@ -19,6 +19,22 @@ function Emeta:__index( key )
return Emetaindex( self, key ) return Emetaindex( self, key )
end end
function Emeta:SetupInventory()
local oldinv = self:GetInventory()
if IsValid( oldinv ) then
print( "[Inventory " .. tostring(oldinv) .. "] Removing to create a new inv" )
oldinv:Remove()
end
local inventory = ents.Create( "inventory" )
if IsValid( inventory ) then
inventory:AttachToEntity( self )
inventory:Spawn()
return inventory
end
return false
end
local Itemmeta = {} local Itemmeta = {}
function Itemmeta:__tostring() function Itemmeta:__tostring()

View File

@ -53,6 +53,23 @@ do -- Base
p:DoCustomAnimEvent( BGESTURE_ITEM1_RIGHT, p:LookupSequence( seqname ) ) p:DoCustomAnimEvent( BGESTURE_ITEM1_RIGHT, p:LookupSequence( seqname ) )
end end
-- Use after children added.
function ITEM:ReevalRecreate()
self:RemoveEFlags( EFL_KEEP_ON_RECREATE_ENTITIES )
if self:GetOwner():IsValid() then
if self:GetOwner():IsEFlagSet( EFL_KEEP_ON_RECREATE_ENTITIES ) then
self:AddEFlags( EFL_KEEP_ON_RECREATE_ENTITIES )
print( "[Item " .. tostring(self) .. "] To be saved during recreate.")
return
else
print( "[Item " .. tostring(self) .. "] Will NOT be saved during recreate.")
return
end
end
print( "[Item " .. tostring(self) .. "] Will NOT be saved during recreate. No owner either")
return
end
function ITEM:EntThink() end function ITEM:EntThink() end
function ITEM:EntPhysicsCollide() end function ITEM:EntPhysicsCollide() end
function ITEM:Reload() end function ITEM:Reload() end
@ -71,6 +88,10 @@ do -- Base
self:GetHandler():SetActiveR( NULL ) self:GetHandler():SetActiveR( NULL )
self:SetNoDraw( true ) self:SetNoDraw( true )
-- LAZY FIX
for i, v in ipairs(self:GetChildren()) do
v:SetNoDraw(true)
end
end end
function ITEM:CancelHolster() function ITEM:CancelHolster()

View File

@ -1,5 +1,4 @@
do -- Base Firearm do -- Base Firearm
local AnimationLookup = { local AnimationLookup = {
["fire"] = { ["fire"] = {
@ -42,7 +41,6 @@ do -- Base Firearm
"Clip", "Clip",
"BurstCount", "BurstCount",
"Firemode", "Firemode",
"ReloadStage",
}, },
["Float"] = { ["Float"] = {
"Delay", "Delay",
@ -52,6 +50,9 @@ do -- Base Firearm
"Accuracy_Amount", "Accuracy_Amount",
"DelayReload", "DelayReload",
}, },
["Entity"] = {
"Inventory"
},
} }
ITEM.Delay = 0.2 ITEM.Delay = 0.2
@ -71,6 +72,10 @@ do -- Base Firearm
function ITEM:EntInitialize() function ITEM:EntInitialize()
Base.EntInitialize( self ) Base.EntInitialize( self )
if SERVER then
local inv = self:SetupInventory()
inv:SetReservedSlots( 1 )
end
end end
function ITEM:Attack() function ITEM:Attack()
@ -133,8 +138,27 @@ do -- Base Firearm
end end
end end
if self:GetRefillTime() != 0 and self:GetRefillTime() <= CurTime() then if self:GetRefillTime() != 0 and self:GetRefillTime() <= CurTime() then
self:SetClip( class.ClipSize ) self:SetClip( self.ClipSize )
self:SetRefillTime( 0 ) self:SetRefillTime( 0 )
if SERVER then
local inv = self:GetInventory()
local ent = ents.Create("b-item_mag_m16a2")
if IsValid(ent) then
ent:AddEffects( EF_BONEMERGE + EF_BONEMERGE_FASTCULL )
ent:SetOwner( self )
ent:SetParent( self )
ent:SetLocalPos( vector_origin )
ent:SetLocalAngles( angle_zero )
ent:Spawn()
self:ReevalRecreate()
ent:ReevalRecreate()
ent:SetMoveType( MOVETYPE_NONE )
inv:SetItem1( ent )
end
end
end end
Base.Think( self ) Base.Think( self )
end end
@ -150,23 +174,52 @@ do -- Base Firearm
local p = self:GetOwner() local p = self:GetOwner()
local time = 0.4 local time = 0.4
if self:GetReloadStage() == 0 then -- Mag loaded if self:GetInventory():GetItem1():IsValid() then -- Mag loaded
-- Unload the mag -- Unload the mag
self:SetReloadStage(1)
self:SetClip( 0 ) self:SetClip( 0 )
self:Sound( self.MagOutSound, 70, 100, 0.4 ) self:Sound( self.MagOutSound, 70, 100, 0.4 )
self:PlayerAnimation( AnimationLookup["reload"][self.HoldType] ) self:PlayerAnimation( AnimationLookup["reload"][self.HoldType] )
self:PlayAnimation( self:LookupSequence( "magout" ) ) self:PlayAnimation( self:LookupSequence( "magout" ) )
time = 0.4 time = 0.4
if CLIENT then
local inv = self:GetInventory()
local curr = inv:GetItem1()
if curr:IsValid() then
local bm = self:GetBoneMatrix( self:LookupBone("Weapon") )
debugoverlay.Cross( bm:GetTranslation(), 16, 0.5 )
local class = ITEMS["mag_m16a2"]
local ent = ents.CreateClientProp( class.Model ) --- TO BE A SHARED ENTITY IN THE FUTURE :3
ent:SetPos( bm:GetTranslation() )
ent:SetAngles( bm:GetAngles() + Angle( 0, -90, -90 ) )
ent:Spawn()
end
end
if SERVER then
local inv = self:GetInventory()
local curr = inv:GetItem1()
if curr:IsValid() then
inv:SetItem1( NULL )
curr:SetOwner( NULL )
curr:SetParent( NULL )
curr:Remove()
self:ReevalRecreate()
-- curr:SetMoveType( MOVETYPE_VPHYSICS )
-- curr:GetPhysicsObject():Wake()
end
end
else else
-- Load it -- Load it
self:SetReloadStage(0) self:SetRefillTime( CurTime() + 0.4 )
self:SetClip( self.ClipSize )
self:Sound( self.MagInSound, 70, 100, 0.4 ) self:Sound( self.MagInSound, 70, 100, 0.4 )
self:PlayerAnimation( AnimationLookup["reload_insert"][self.HoldType] ) self:PlayerAnimation( AnimationLookup["reload_insert"][self.HoldType] )
self:PlayAnimation( self:LookupSequence( "magin" ) ) self:PlayAnimation( self:LookupSequence( "magin" ) )
time = 0.8
end end
time = 0.8
self:SetDelay( CurTime() + time ) self:SetDelay( CurTime() + time )
end end
@ -186,6 +239,14 @@ do -- Base Firearm
Base.CancelHolster( self ) Base.CancelHolster( self )
end end
do -- Base Mag
local ITEM, Base = CreateItem( "base_mag", "base" )
ITEM.PrintName = "Magazine Base"
ITEM.Description = "Testing testing"
ITEM.Category = "base"
end
do -- Handguns do -- Handguns
do -- G18 do -- G18
local ITEM, Base = CreateItem( "g18", "base_firearm" ) local ITEM, Base = CreateItem( "g18", "base_firearm" )
@ -262,6 +323,20 @@ do -- Base Firearm
ITEM.MagInSound = bSound("weapons/m16a2/magin.ogg") ITEM.MagInSound = bSound("weapons/m16a2/magin.ogg")
ITEM.BoltDropSound = bSound("weapons/m16a2/cock.ogg") ITEM.BoltDropSound = bSound("weapons/m16a2/cock.ogg")
ITEM.BoltPullSound = bSound("weapons/fnc/cock.ogg") ITEM.BoltPullSound = bSound("weapons/fnc/cock.ogg")
do
local ITEM, Base = CreateItem( "mag_m16a2", "base_mag" )
ITEM.PrintName = "#Item.mag_m16a2.Name"
ITEM.Description = "#Item.mag_m16a2.Description"
ITEM.Category = "magazine"
ITEM.Model = bModel("weapons/test_m16a2_mag")
ITEM.DefaultBodygroups = {}
ITEM.HoldType = "magazine"
ITEM.ClipSize = 30
end
end end
end end
end end

View File

@ -44,6 +44,8 @@ function GM:PlayerSpawn( ply )
ply:SetHealth_Blood( 1000 ) ply:SetHealth_Blood( 1000 )
ply:SetHealth_Stamina( 1000 ) ply:SetHealth_Stamina( 1000 )
ply:SetupInventory()
ply:MakeCharacter() ply:MakeCharacter()
end end

View File

@ -47,6 +47,7 @@ function PLAYER:SetupDataTables()
self.Player:NetworkVar( "Float", "DivedAt" ) self.Player:NetworkVar( "Float", "DivedAt" )
self.Player:NetworkVar( "Float", "TouchedObjectiveTime" ) self.Player:NetworkVar( "Float", "TouchedObjectiveTime" )
self.Player:NetworkVar( "Entity", "Inventory" )
self.Player:NetworkVar( "Entity", "TouchedObjective" ) self.Player:NetworkVar( "Entity", "TouchedObjective" )
self.Player:NetworkVar( "Vector", "VaultPos1") self.Player:NetworkVar( "Vector", "VaultPos1")