mirror of
https://github.com/lifestorm/wnsrc.git
synced 2025-12-16 21:33:46 +03:00
Upload
This commit is contained in:
143
addons/weapon_holsters/lua/autorun/client/cl_weapon_holsters.lua
Normal file
143
addons/weapon_holsters/lua/autorun/client/cl_weapon_holsters.lua
Normal file
@@ -0,0 +1,143 @@
|
||||
--[[
|
||||
| This file was obtained through the combined efforts
|
||||
| of Madbluntz & Plymouth Antiquarian Society.
|
||||
|
|
||||
| Credits: lifestorm, Gregory Wayne Rossel JR.,
|
||||
| Maloy, DrPepper10 @ RIP, Atle!
|
||||
|
|
||||
| Visit for more: https://plymouth.thetwilightzone.ru/
|
||||
--]]
|
||||
|
||||
--[[
|
||||
__ ___ __ __
|
||||
/ |/ /__ ____/ /__ / / __ __
|
||||
/ /|_/ / _ `/ _ / -_) / _ \/ // /
|
||||
/_/ /_/\_,_/\_,_/\__/ /_.__/\_, /
|
||||
___ __ /___/ ___ __
|
||||
/ _ \___ / /_ _____ ___ / /____ ____ / _ \__ ______/ /__
|
||||
/ ___/ _ \/ / // / -_|_-</ __/ -_) __/ / // / // / __/ '_/
|
||||
/_/ \___/_/\_, /\__/___/\__/\__/_/ /____/\_,_/\__/_/\_\
|
||||
/___/
|
||||
https://steamcommunity.com/profiles/76561198057599363
|
||||
]]
|
||||
CreateClientConVar("cl_weapon_holsters", "1", true, false, "Enable Weapon Holsters (client side)")
|
||||
WepHolster = WepHolster or {}
|
||||
WepHolster.wepInfo = WepHolster.wepInfo or {}
|
||||
|
||||
net.Receive("sendWholeWHData", function(len)
|
||||
WepHolster.wepInfo = net.ReadTable()
|
||||
end)
|
||||
|
||||
net.Receive("sendWHData", function(len)
|
||||
local class = net.ReadString()
|
||||
local tbl = net.ReadTable()
|
||||
WepHolster.wepInfo[class] = tbl.Model and tbl or nil
|
||||
|
||||
if not tbl.Model then
|
||||
for pl, weps in pairs(WepHolster.HolsteredWeps) do
|
||||
local ply = Entity(pl)
|
||||
|
||||
for cls, wep in pairs(weps) do
|
||||
if cls == class then
|
||||
wep:Remove()
|
||||
WepHolster.HolsteredWeps[pl][cls] = nil
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
||||
WepHolster.HolsteredWeps = WepHolster.HolsteredWeps or {}
|
||||
|
||||
local function CalcOffset(pos, ang, off)
|
||||
return pos + ang:Right() * off.x + ang:Forward() * off.y + ang:Up() * off.z
|
||||
end
|
||||
|
||||
local function cdwh()
|
||||
return WepHolster.wepInfo and WepHolster.HolsteredWeps and GetConVar("cl_weapon_holsters"):GetBool() and GetConVar("sv_weapon_holsters"):GetBool()
|
||||
end
|
||||
|
||||
hook.Add("PostPlayerDraw", "WeaponHolster", function(ply)
|
||||
if not cdwh() then
|
||||
return
|
||||
end
|
||||
|
||||
if IsValid(ply) and ply:Alive() then
|
||||
for wepclass, model in pairs(WepHolster.HolsteredWeps[ply:EntIndex()] or {}) do
|
||||
if not WepHolster.wepInfo[wepclass] then
|
||||
return
|
||||
end
|
||||
|
||||
local bone = ply:LookupBone(WepHolster.wepInfo[wepclass].Bone)
|
||||
|
||||
if not bone then
|
||||
return
|
||||
end
|
||||
|
||||
local matrix = ply:GetBoneMatrix(bone)
|
||||
|
||||
if not matrix then
|
||||
return
|
||||
end
|
||||
|
||||
local pos = matrix:GetTranslation()
|
||||
local ang = matrix:GetAngles()
|
||||
pos = CalcOffset(pos, ang, WepHolster.wepInfo[wepclass].BoneOffset[1])
|
||||
model:SetRenderOrigin(pos)
|
||||
ang:RotateAroundAxis(ang:Forward(), WepHolster.wepInfo[wepclass].BoneOffset[2].p)
|
||||
ang:RotateAroundAxis(ang:Up(), WepHolster.wepInfo[wepclass].BoneOffset[2].y)
|
||||
ang:RotateAroundAxis(ang:Right(), WepHolster.wepInfo[wepclass].BoneOffset[2].r)
|
||||
model:SetRenderAngles(ang)
|
||||
model:DrawModel()
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
||||
hook.Add("Think", "WeaponHolster", function()
|
||||
if not cdwh() then
|
||||
return
|
||||
end
|
||||
|
||||
for _, ply in pairs(player.GetAll()) do
|
||||
if IsValid(ply) and ply:Alive() then
|
||||
for k, v in pairs(ply:GetWeapons()) do
|
||||
local class = v:GetClass()
|
||||
local plyid = ply:EntIndex()
|
||||
WepHolster.HolsteredWeps[plyid] = WepHolster.HolsteredWeps[plyid] or {}
|
||||
|
||||
if WepHolster.wepInfo[class] and ply:GetActiveWeapon() ~= v and not WepHolster.HolsteredWeps[plyid][class] then
|
||||
WepHolster.HolsteredWeps[plyid][class] = ClientsideModel(WepHolster.wepInfo[class].Model, RENDERGROUP_OPAQUE)
|
||||
|
||||
if not IsValid(WepHolster.HolsteredWeps[plyid][class]) then
|
||||
SafeRemoveEntity(WepHolster.HolsteredWeps[plyid][class]) -- just in case.
|
||||
WepHolster.HolsteredWeps[plyid][class] = nil
|
||||
|
||||
return
|
||||
end
|
||||
|
||||
WepHolster.HolsteredWeps[plyid][class]:SetNoDraw(true)
|
||||
|
||||
if WepHolster.wepInfo[class].isEditing then
|
||||
WepHolster.HolsteredWeps[plyid][class]:SetMaterial("models/wireframe")
|
||||
--print("wireframe화 think")
|
||||
--print(WepHolster.wepInfo[class].isEditing)
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
-- 필요없는 CSEnt 찾아서 삭제
|
||||
for pl, weps in pairs(WepHolster.HolsteredWeps) do
|
||||
local ply = Entity(pl)
|
||||
|
||||
for class, wep in pairs(weps) do
|
||||
if not IsValid(ply) or not ply:IsPlayer() or not ply:Alive() or (IsValid(ply:GetActiveWeapon()) and ply:GetActiveWeapon():GetClass() == class) or not IsValid(ply:GetWeapon(class)) then
|
||||
wep:Remove() -- 삭제
|
||||
WepHolster.HolsteredWeps[pl][class] = nil
|
||||
|
||||
return
|
||||
end
|
||||
end
|
||||
end
|
||||
end)
|
||||
678
addons/weapon_holsters/lua/autorun/client/wh_gui.lua
Normal file
678
addons/weapon_holsters/lua/autorun/client/wh_gui.lua
Normal file
@@ -0,0 +1,678 @@
|
||||
--[[
|
||||
| This file was obtained through the combined efforts
|
||||
| of Madbluntz & Plymouth Antiquarian Society.
|
||||
|
|
||||
| Credits: lifestorm, Gregory Wayne Rossel JR.,
|
||||
| Maloy, DrPepper10 @ RIP, Atle!
|
||||
|
|
||||
| Visit for more: https://plymouth.thetwilightzone.ru/
|
||||
--]]
|
||||
|
||||
--[[
|
||||
__ ___ __ __
|
||||
/ |/ /__ ____/ /__ / / __ __
|
||||
/ /|_/ / _ `/ _ / -_) / _ \/ // /
|
||||
/_/ /_/\_,_/\_,_/\__/ /_.__/\_, /
|
||||
___ __ /___/ ___ __
|
||||
/ _ \___ / /_ _____ ___ / /____ ____ / _ \__ ______/ /__
|
||||
/ ___/ _ \/ / // / -_|_-</ __/ -_) __/ / // / // / __/ '_/
|
||||
/_/ \___/_/\_, /\__/___/\__/\__/_/ /____/\_,_/\__/_/\_\
|
||||
/___/
|
||||
https://steamcommunity.com/profiles/76561198057599363
|
||||
]]
|
||||
local Menu = {
|
||||
Main = {},
|
||||
Editor = {}
|
||||
}
|
||||
|
||||
local playerBones = {"ValveBiped.Bip01_Head1", "ValveBiped.Bip01_Pelvis", "ValveBiped.Bip01_Spine", "ValveBiped.Bip01_Spine1", "ValveBiped.Bip01_Spine2", "ValveBiped.Bip01_Spine4", "ValveBiped.Anim_Attachment_RH", "ValveBiped.Bip01_R_Hand", "ValveBiped.Bip01_R_Forearm", "ValveBiped.Bip01_R_UpperArm", "ValveBiped.Bip01_R_Clavicle", "ValveBiped.Bip01_R_Foot", "ValveBiped.Bip01_R_Toe0", "ValveBiped.Bip01_R_Thigh", "ValveBiped.Bip01_R_Calf", "ValveBiped.Bip01_R_Shoulder", "ValveBiped.Bip01_R_Elbow", "ValveBiped.Bip01_Neck1", "ValveBiped.Anim_Attachment_LH", "ValveBiped.Bip01_L_Hand", "ValveBiped.Bip01_L_Forearm", "ValveBiped.Bip01_L_UpperArm", "ValveBiped.Bip01_L_Clavicle", "ValveBiped.Bip01_L_Foot", "ValveBiped.Bip01_L_Toe0", "ValveBiped.Bip01_L_Thigh", "ValveBiped.Bip01_L_Calf", "ValveBiped.Bip01_L_Shoulder", "ValveBiped.Bip01_L_Elbow"}
|
||||
|
||||
local function KeyboardOn(pnl)
|
||||
if (IsValid(Menu.Main.Frame) and IsValid(pnl) and pnl:HasParent(Menu.Main.Frame)) then
|
||||
Menu.Main.Frame:SetKeyboardInputEnabled(true)
|
||||
end
|
||||
end
|
||||
|
||||
hook.Add("OnTextEntryGetFocus", "lf_weapon_properties_editor_keyboard_on", KeyboardOn)
|
||||
|
||||
local function KeyboardOff(pnl)
|
||||
if (IsValid(Menu.Main.Frame) and IsValid(pnl) and pnl:HasParent(Menu.Main.Frame)) then
|
||||
Menu.Main.Frame:SetKeyboardInputEnabled(false)
|
||||
|
||||
if pnl.OnValueChange then
|
||||
pnl:OnValueChange()
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
hook.Add("OnTextEntryLoseFocus", "lf_weapon_properties_editor_keyboard_off", KeyboardOff)
|
||||
-- Blur Code by: https://facepunch.com/member.php?u=237675
|
||||
local blur = Material("pp/blurscreen")
|
||||
|
||||
local function DrawBlur(panel, amount)
|
||||
local x, y = panel:LocalToScreen(0, 0)
|
||||
local scrW, scrH = ScrW(), ScrH()
|
||||
surface.SetDrawColor(255, 255, 255)
|
||||
surface.SetMaterial(blur)
|
||||
|
||||
for i = 1, 3 do
|
||||
blur:SetFloat("$blur", (i / 3) * (amount or 6))
|
||||
blur:Recompute()
|
||||
render.UpdateScreenEffectTexture()
|
||||
surface.DrawTexturedRect(x * -1, y * -1, scrW, scrH)
|
||||
end
|
||||
end
|
||||
|
||||
local function removeHolstWep(class)
|
||||
for pl, weps in pairs(WepHolster.HolsteredWeps) do
|
||||
for cls, wep in pairs(weps) do
|
||||
if class == "" or cls == class then
|
||||
wep:Remove()
|
||||
WepHolster.HolsteredWeps[pl][cls] = nil
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
local function setEditing(class, bool)
|
||||
if class ~= "" then
|
||||
if WepHolster.wepInfo[class] then
|
||||
WepHolster.wepInfo[class].isEditing = bool
|
||||
end
|
||||
else
|
||||
for k, v in pairs(WepHolster.wepInfo) do
|
||||
WepHolster.wepInfo[k].isEditing = bool
|
||||
end
|
||||
end
|
||||
|
||||
for pl, weps in pairs(WepHolster.HolsteredWeps) do
|
||||
for cls, wep in pairs(weps) do
|
||||
if cls == class or class == "" then
|
||||
if bool then
|
||||
wep:SetMaterial("models/wireframe")
|
||||
--print("wireframe화 gui")
|
||||
--print(WepHolster.wepInfo[cls].isEditing)
|
||||
--print("wireframe 해제 gui")
|
||||
--print(WepHolster.wepInfo[cls].isEditing)
|
||||
else
|
||||
wep:Remove()
|
||||
WepHolster.HolsteredWeps[pl][cls] = nil
|
||||
WepHolster.wepInfo[cls].isEditing = nil
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
function Menu.Editor:Init(class)
|
||||
local Frame = vgui.Create("DFrame", Menu.Main.Frame)
|
||||
local fw, fh = 600, 350
|
||||
local pw, ph = fw - 10, fh - 34
|
||||
Frame:SetPos(ScrW() - fw - 10, (ScrH() / 2) - (fh / 2))
|
||||
Frame:SetSize(fw, fh)
|
||||
Frame:SetTitle(class)
|
||||
Frame:SetVisible(true)
|
||||
Frame:SetDraggable(true)
|
||||
Frame:SetScreenLock(false)
|
||||
Frame:ShowCloseButton(true)
|
||||
Frame:MakePopup()
|
||||
Frame:SetKeyboardInputEnabled(false)
|
||||
|
||||
function Frame:Paint(w, h)
|
||||
DrawBlur(self, 2)
|
||||
draw.RoundedBox(0, 0, 0, w, h, Color(0, 0, 0, 200))
|
||||
|
||||
return true
|
||||
end
|
||||
|
||||
function Frame.lblTitle:Paint(w, h)
|
||||
draw.SimpleTextOutlined(Frame.lblTitle:GetText(), "DermaDefaultBold", 1, 2, Color(255, 255, 255, 255), 0, 0, 1, Color(0, 0, 0, 255))
|
||||
|
||||
return true
|
||||
end
|
||||
|
||||
local pnl = Frame:Add("DPanel")
|
||||
pnl:Dock(FILL)
|
||||
pnl:DockPadding(10, 10, 10, 10)
|
||||
local prop = pnl:Add("DCategoryList")
|
||||
prop:Dock(FILL)
|
||||
|
||||
local function AddLineText(list, text, val, class)
|
||||
local line = list:Add("DPanel")
|
||||
line:DockPadding(5, 2, 5, 2)
|
||||
line:SetDrawBackground(false)
|
||||
local id
|
||||
|
||||
if val then
|
||||
local lbl = line:Add("DLabel")
|
||||
lbl:Dock(LEFT)
|
||||
lbl:SetWide(239)
|
||||
lbl:SetDark(true)
|
||||
lbl:SetText(text)
|
||||
id = line:Add("DTextEntry")
|
||||
id:Dock(FILL)
|
||||
id:SetText(val or "")
|
||||
else
|
||||
local lbl = line:Add("DLabel")
|
||||
lbl:Dock(FILL)
|
||||
lbl:SetText(text)
|
||||
end
|
||||
|
||||
return line, id
|
||||
end
|
||||
|
||||
local function AddLineInt(list, text, val, min, max)
|
||||
local line = list:Add("DPanel")
|
||||
line:DockPadding(5, 2, 5, 2)
|
||||
line:SetPaintBackground(false)
|
||||
local id
|
||||
|
||||
if val then
|
||||
id = line:Add("DNumSlider")
|
||||
id:Dock(FILL)
|
||||
id:SetDark(true)
|
||||
id:SetDecimals(3)
|
||||
id:SetMinMax(min, max)
|
||||
id:SetText(text)
|
||||
id:SetValue(val or 0)
|
||||
else
|
||||
local lbl = line:Add("DLabel")
|
||||
lbl:Dock(FILL)
|
||||
lbl:SetText(text)
|
||||
end
|
||||
|
||||
return line, id
|
||||
end
|
||||
|
||||
local cat = prop:Add(class)
|
||||
local list = vgui.Create("DListLayout")
|
||||
cat:SetContents(list)
|
||||
local line, rModel = AddLineText(list, "Model:", WepHolster.wepInfo[class].Model, class)
|
||||
|
||||
rModel.OnValueChange = function(val)
|
||||
val = rModel:GetValue()
|
||||
WepHolster.wepInfo[class].Model = val
|
||||
setEditing(class, true)
|
||||
removeHolstWep(class)
|
||||
end
|
||||
|
||||
local line, rBone = AddLineText(list, "Bone:", WepHolster.wepInfo[class].Bone)
|
||||
WepHolster.lookingBone = WepHolster.wepInfo[class].Bone
|
||||
|
||||
if rBone then
|
||||
rBone.OnValueChange = function(val)
|
||||
val = rBone:GetValue()
|
||||
|
||||
if table.HasValue(playerBones, val) then
|
||||
WepHolster.wepInfo[class].Bone = val
|
||||
setEditing(class, true)
|
||||
WepHolster.lookingBone = val
|
||||
end
|
||||
end
|
||||
|
||||
local c = line:Add("DComboBox")
|
||||
c:Dock(RIGHT)
|
||||
c:SetWide(40)
|
||||
c:SetSortItems(false)
|
||||
c:SetValue("...")
|
||||
|
||||
for _, v in pairs(playerBones) do
|
||||
c:AddChoice(v)
|
||||
end
|
||||
|
||||
function c:OnSelect(index, value)
|
||||
rBone:SetText(value)
|
||||
rBone:OnValueChange()
|
||||
c:SetValue("...")
|
||||
end
|
||||
end
|
||||
|
||||
local line, rVectorX = AddLineInt(list, "Position x:", WepHolster.wepInfo[class].BoneOffset[1].x, -20, 20, class)
|
||||
|
||||
rVectorX.OnValueChanged = function(value)
|
||||
WepHolster.wepInfo[class].BoneOffset[1].x = rVectorX:GetValue()
|
||||
setEditing(class, true)
|
||||
end
|
||||
|
||||
local line, rVectorY = AddLineInt(list, "Position y:", WepHolster.wepInfo[class].BoneOffset[1].y, -20, 20, class)
|
||||
|
||||
rVectorY.OnValueChanged = function(value)
|
||||
WepHolster.wepInfo[class].BoneOffset[1].y = rVectorY:GetValue()
|
||||
setEditing(class, true)
|
||||
end
|
||||
|
||||
local line, rVectorZ = AddLineInt(list, "Position z:", WepHolster.wepInfo[class].BoneOffset[1].z, -20, 20, class)
|
||||
|
||||
rVectorZ.OnValueChanged = function(value)
|
||||
WepHolster.wepInfo[class].BoneOffset[1].z = rVectorZ:GetValue()
|
||||
setEditing(class, true)
|
||||
end
|
||||
|
||||
local line, rAngleP = AddLineInt(list, "Angle pitch:", WepHolster.wepInfo[class].BoneOffset[2].p, -180, 180, class)
|
||||
|
||||
rAngleP.OnValueChanged = function(value)
|
||||
WepHolster.wepInfo[class].BoneOffset[2].p = rAngleP:GetValue()
|
||||
setEditing(class, true)
|
||||
end
|
||||
|
||||
local line, rAngleY = AddLineInt(list, "Angle yaw:", WepHolster.wepInfo[class].BoneOffset[2].y, -180, 180, class)
|
||||
|
||||
rAngleY.OnValueChanged = function(value)
|
||||
WepHolster.wepInfo[class].BoneOffset[2].y = rAngleY:GetValue()
|
||||
setEditing(class, true)
|
||||
end
|
||||
|
||||
local line, rAngleR = AddLineInt(list, "Angle roll:", WepHolster.wepInfo[class].BoneOffset[2].r, -180, 180, class)
|
||||
|
||||
rAngleR.OnValueChanged = function(value)
|
||||
WepHolster.wepInfo[class].BoneOffset[2].r = rAngleR:GetValue()
|
||||
setEditing(class, true)
|
||||
end
|
||||
|
||||
local subpnl = pnl:Add("DPanel")
|
||||
subpnl:Dock(BOTTOM)
|
||||
subpnl:DockMargin(0, 20, 0, 0)
|
||||
subpnl:SetHeight(20)
|
||||
subpnl:SetDrawBackground(false)
|
||||
local lw = (pw - 10) / 2 - 10
|
||||
local b = subpnl:Add("DComboBox")
|
||||
b:Dock(LEFT)
|
||||
b:SetWide(lw)
|
||||
b:SetValue("Reset")
|
||||
b:SetSortItems(false)
|
||||
b:AddChoice("to saved data if available")
|
||||
b:AddChoice("to default if available")
|
||||
|
||||
b.OnSelect = function(index, value, data)
|
||||
Frame:Close()
|
||||
|
||||
if value == 2 then
|
||||
local oldwhdata = WepHolster.wepInfo[class]
|
||||
net.Start("resetWHDataToDefault")
|
||||
net.WriteString(class)
|
||||
net.SendToServer()
|
||||
|
||||
timer.Simple(0.1, function()
|
||||
local different
|
||||
|
||||
for k, v in pairs(WepHolster.wepInfo[class]) do
|
||||
if (k == "Model" or k == "Bone") and string.lower(oldwhdata[k]) ~= string.lower(v) then
|
||||
different = true
|
||||
print(k .. ": " .. v)
|
||||
-- print(_..": "..vec_ang)
|
||||
elseif k == "BoneOffset" then
|
||||
for _, vec_ang in pairs(v) do
|
||||
if vec_ang ~= oldwhdata[k][_] then
|
||||
different = true
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
-- '==' operator is not working on table.. fuck.
|
||||
if different then
|
||||
setEditing(class, true)
|
||||
end
|
||||
end)
|
||||
elseif not WepHolster.wepInfo[class].notSavedYet then
|
||||
net.Start("reloadWH")
|
||||
net.WriteString(class)
|
||||
net.SendToServer()
|
||||
setEditing(class, false)
|
||||
end
|
||||
|
||||
timer.Simple(0.1, function()
|
||||
Menu.Editor:Init(class)
|
||||
removeHolstWep(class)
|
||||
end)
|
||||
end
|
||||
|
||||
local b = subpnl:Add("DComboBox")
|
||||
b:Dock(RIGHT)
|
||||
b:SetWide(lw)
|
||||
b:SetValue("Delete")
|
||||
b:AddChoice("Are you sure?")
|
||||
|
||||
b.OnSelect = function(index, value, data)
|
||||
net.Start("deleteWHData")
|
||||
net.WriteString(class)
|
||||
net.SendToServer()
|
||||
|
||||
timer.Simple(0.1, function()
|
||||
Menu.Main.Frame:Close()
|
||||
Menu.Main:Init()
|
||||
end)
|
||||
end
|
||||
|
||||
local b = pnl:Add("DButton")
|
||||
b:Dock(BOTTOM)
|
||||
b:DockMargin(0, 10, 0, 0)
|
||||
b:SetHeight(30)
|
||||
b:SetText("Apply Changes")
|
||||
|
||||
b.DoClick = function()
|
||||
setEditing(class, false)
|
||||
WepHolster.wepInfo[class].notSavedYet = nil
|
||||
net.Start("applyWepHolsterData")
|
||||
net.WriteString(class)
|
||||
net.WriteTable(WepHolster.wepInfo[class])
|
||||
net.SendToServer()
|
||||
Frame:Close()
|
||||
end
|
||||
|
||||
Frame.OnClose = function()
|
||||
--[[
|
||||
net.Start("reloadWH")
|
||||
net.WriteString(class)
|
||||
net.SendToServer()
|
||||
Menu.Main.Frame:Close()
|
||||
timer.Simple(0.1, function()
|
||||
removeHolstWep(class)
|
||||
Menu.Main:Init()
|
||||
end)
|
||||
]]
|
||||
WepHolster.lookingBone = nil
|
||||
end
|
||||
end
|
||||
|
||||
local function addWeapon(class, model)
|
||||
WepHolster.wepInfo[class] = WepHolster.wepInfo[class] or {
|
||||
Model = model or "models/weapons/w_rif_ak47.mdl",
|
||||
Bone = "ValveBiped.Bip01_R_Clavicle",
|
||||
BoneOffset = {Vector(13, 4, 5), Angle(90, 0, 100)},
|
||||
notSavedYet = true
|
||||
}
|
||||
|
||||
Menu.Main.Frame:Close()
|
||||
Menu.Main:Init()
|
||||
Menu.Editor:Init(class)
|
||||
setEditing(class, true)
|
||||
end
|
||||
|
||||
function Menu.Main:Init()
|
||||
Menu.Main.Frame = vgui.Create("DFrame")
|
||||
local Frame = Menu.Main.Frame
|
||||
local fw, fh = 400, ScrH() - 20
|
||||
local pw, ph = fw - 10, fh - 34
|
||||
Frame:SetPos(10, 10)
|
||||
Frame:SetSize(fw, fh)
|
||||
Frame:SetTitle("Weapon Holsters Editor")
|
||||
Frame:SetVisible(true)
|
||||
Frame:SetDraggable(true)
|
||||
Frame:SetScreenLock(false)
|
||||
Frame:ShowCloseButton(true)
|
||||
Frame:MakePopup()
|
||||
Frame:SetKeyboardInputEnabled(false)
|
||||
|
||||
function Frame:Paint(w, h)
|
||||
DrawBlur(self, 2)
|
||||
draw.RoundedBox(0, 0, 0, w, h, Color(0, 0, 0, 200))
|
||||
|
||||
return true
|
||||
end
|
||||
|
||||
function Frame.lblTitle:Paint(w, h)
|
||||
draw.SimpleTextOutlined(Frame.lblTitle:GetText(), "DermaDefaultBold", 1, 2, Color(255, 255, 255, 255), 0, 0, 1, Color(0, 0, 0, 255))
|
||||
|
||||
return true
|
||||
end
|
||||
|
||||
local pnl = Frame:Add("DPanel")
|
||||
pnl:Dock(FILL)
|
||||
pnl:DockPadding(10, 10, 10, 10)
|
||||
local b = pnl:Add("DButton")
|
||||
b:Dock(TOP)
|
||||
b:DockMargin(0, 0, 0, 1)
|
||||
b:SetHeight(25)
|
||||
b:SetText("Add weapon by class:")
|
||||
|
||||
b.DoClick = function()
|
||||
local name = tostring(Menu.Main.WeaponEntry:GetValue())
|
||||
|
||||
if name == "" then
|
||||
return
|
||||
end
|
||||
|
||||
addWeapon(name)
|
||||
end
|
||||
|
||||
Menu.Main.WeaponEntry = pnl:Add("DTextEntry")
|
||||
Menu.Main.WeaponEntry:Dock(TOP)
|
||||
Menu.Main.WeaponEntry:DockMargin(0, 0, 0, 10)
|
||||
Menu.Main.WeaponEntry:SetHeight(20)
|
||||
Menu.Main.WeaponEntry:SetTooltip("Just right-click on the weapon icon in the spawn menu, click Copy to Clipboard, and paste it here.")
|
||||
--[[
|
||||
local help = pnl:Add("DLabel") -- Fuck you, I'll use SetTooltip instead.
|
||||
help:Dock(TOP)
|
||||
help:DockMargin(0, 0, 0, 10)
|
||||
help:SetHeight(26)
|
||||
help:SetText("Just right-click on the weapon icon in the spawn menu,\nclick Copy to Clipboard, and paste it here.")
|
||||
]]
|
||||
b = pnl:Add("DButton")
|
||||
b:Dock(TOP)
|
||||
b:DockMargin(0, 0, 0, 10)
|
||||
b:SetHeight(24)
|
||||
b:SetText("Add weapon you currently holding")
|
||||
|
||||
b.DoClick = function()
|
||||
local weapon = LocalPlayer():GetActiveWeapon()
|
||||
|
||||
if IsValid(weapon) then
|
||||
addWeapon(weapon:GetClass(), weapon:GetWeaponWorldModel())
|
||||
end
|
||||
end
|
||||
|
||||
--[[
|
||||
local help = pnl:Add("DLabel")
|
||||
help:Dock(TOP)
|
||||
help:DockMargin(0, 0, 0, 5)
|
||||
help:SetHeight(13)
|
||||
help:SetText("Click the bar to sort the list, and double click the weapon to edit:")
|
||||
]]
|
||||
Menu.Main.WeaponList = pnl:Add("DListView")
|
||||
Menu.Main.WeaponList:Dock(FILL)
|
||||
Menu.Main.WeaponList:SetMultiSelect(false)
|
||||
Menu.Main.WeaponList:AddColumn("Category")
|
||||
Menu.Main.WeaponList:AddColumn("Name")
|
||||
Menu.Main.WeaponList:AddColumn("Class")
|
||||
Menu.Main.WeaponList:SetTooltip("Click the bar to sort the list, and double click the weapon to edit.")
|
||||
|
||||
function Menu.Main.WeaponList:DoDoubleClick(id, sel)
|
||||
local wepclass = tostring(sel:GetValue(3))
|
||||
|
||||
if WepHolster.wepInfo[wepclass] then
|
||||
Menu.Editor:Init(wepclass)
|
||||
end
|
||||
end
|
||||
|
||||
function Menu.Main.WeaponList:Populate()
|
||||
self:Clear()
|
||||
|
||||
for k, v in pairs(WepHolster.wepInfo) do
|
||||
local swep = weapons.Get(k)
|
||||
self:AddLine(swep and swep.Category or "Other", swep and swep.PrintName or WepHolster.HL2Weps[k] or k, k)
|
||||
end
|
||||
|
||||
self:SortByColumn(1)
|
||||
end
|
||||
|
||||
Menu.Main.WeaponList:Populate()
|
||||
local credit = pnl:Add("DLabel")
|
||||
credit:Dock(BOTTOM)
|
||||
credit:DockMargin(0, 10, 0, 0)
|
||||
credit:SetHeight(13)
|
||||
credit:SetText("Made by Polyester Duck")
|
||||
local b = pnl:Add("DComboBox")
|
||||
b:Dock(BOTTOM)
|
||||
b:DockMargin(0, 10, 0, 0)
|
||||
b:SetHeight(20)
|
||||
b:SetValue("RESET EVERYTHING TO DEFAULT")
|
||||
b:AddChoice("ARE YOU REALLY SURE?")
|
||||
|
||||
b.OnSelect = function(index, value, data)
|
||||
setEditing("", false)
|
||||
net.Start("resetWholeWHDataToDefault")
|
||||
net.SendToServer()
|
||||
Frame:Close()
|
||||
timer.Simple(0.1, Menu.Main.Init)
|
||||
end
|
||||
|
||||
Frame.OnClose = function()
|
||||
--[[
|
||||
net.Start("reloadWholeWH")
|
||||
net.SendToServer()
|
||||
for pl, weps in pairs(WepHolster.HolsteredWeps) do
|
||||
for cls, wep in pairs(weps) do
|
||||
wep:Remove()
|
||||
WepHolster.HolsteredWeps[pl][cls] = nil
|
||||
end
|
||||
end
|
||||
]]
|
||||
WepHolster.lookingBone = nil
|
||||
end
|
||||
end
|
||||
|
||||
function Menu.Toggle()
|
||||
if LocalPlayer():IsSuperAdmin() then
|
||||
if IsValid(Menu.Main.Frame) then
|
||||
Menu.Main.Frame:Close()
|
||||
else
|
||||
Menu.Main:Init()
|
||||
end
|
||||
else
|
||||
if IsValid(Menu.Main.Frame) then
|
||||
Menu.Main.Frame:Close()
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
concommand.Add("weapon_holsters_editor", Menu.Toggle)
|
||||
|
||||
local function clientTrickBox(panel, con_name, func_onchange)
|
||||
local con = GetConVar(con_name)
|
||||
|
||||
if not con then
|
||||
return
|
||||
end
|
||||
|
||||
local tickbox = vgui.Create("DCheckBoxLabel", panel)
|
||||
tickbox:SetText(con:GetHelpText() or "Unknown setting.")
|
||||
tickbox:SetValue(con:GetBool())
|
||||
tickbox.con_name = con_name
|
||||
tickbox:SetDark(true)
|
||||
|
||||
function tickbox:OnChange(b)
|
||||
RunConsoleCommand(self.con_name, b and "1" or "0")
|
||||
|
||||
if func_onchange then
|
||||
func_onchange()
|
||||
end
|
||||
end
|
||||
|
||||
function tickbox:Think()
|
||||
if not self.con_name then
|
||||
return
|
||||
end
|
||||
|
||||
local ucon = GetConVar(self.con_name)
|
||||
|
||||
if (ucon:GetBool() or true) ~= self:GetValue() then
|
||||
self:SetChecked(ucon:GetBool())
|
||||
end
|
||||
end
|
||||
|
||||
panel:AddItem(tickbox)
|
||||
end
|
||||
|
||||
local function requestSetting(con, arg)
|
||||
if type(arg) == "boolean" then
|
||||
arg = arg and "1" or "0"
|
||||
end
|
||||
|
||||
net.Start("WepHolsters_Settings")
|
||||
net.WriteString(con)
|
||||
net.WriteString(arg)
|
||||
net.SendToServer()
|
||||
end
|
||||
|
||||
local function adminTrickBox(panel, con_name)
|
||||
local con = GetConVar(con_name)
|
||||
|
||||
if not con then
|
||||
return
|
||||
end
|
||||
|
||||
local tickbox = vgui.Create("DCheckBoxLabel", panel)
|
||||
tickbox:SetText(con:GetHelpText() or "Unknown setting.")
|
||||
tickbox:SetValue(con:GetBool())
|
||||
tickbox.con_name = con_name
|
||||
tickbox:SetDark(true)
|
||||
|
||||
function tickbox:OnChange(b)
|
||||
requestSetting(self.con_name, b and "1" or "0")
|
||||
end
|
||||
|
||||
function tickbox:Think()
|
||||
if not self.con_name then
|
||||
return
|
||||
end
|
||||
|
||||
local ucon = GetConVar(self.con_name)
|
||||
|
||||
if (ucon:GetBool() or true) ~= self:GetValue() then
|
||||
self:SetChecked(ucon:GetBool())
|
||||
end
|
||||
end
|
||||
|
||||
panel:AddItem(tickbox)
|
||||
end
|
||||
|
||||
-- Spawn Menu entry.
|
||||
local function SpawnMenu_Entry(panel)
|
||||
panel:AddControl("Label", {
|
||||
Text = "Client Settings:"
|
||||
})
|
||||
|
||||
clientTrickBox(panel, "cl_weapon_holsters", function()
|
||||
removeHolstWep("")
|
||||
end)
|
||||
|
||||
panel:AddControl("Label", {
|
||||
Text = "Administrator Settings:"
|
||||
})
|
||||
|
||||
adminTrickBox(panel, "sv_weapon_holsters")
|
||||
|
||||
local a = panel:AddControl("Button", {
|
||||
Label = "Open Editor",
|
||||
Command = "weapon_holsters_editor"
|
||||
})
|
||||
|
||||
a:SetSize(0, 50)
|
||||
a:SetEnabled(LocalPlayer():IsSuperAdmin())
|
||||
end
|
||||
|
||||
hook.Add("PopulateToolMenu", "weapon_holsters_editor_spawnmenu", function()
|
||||
spawnmenu.AddToolMenuOption("Options", "Player", "weapon_holsters_editor_spawnmenu_entry", "Weapon Holsters", "", "", SpawnMenu_Entry, {})
|
||||
end)
|
||||
|
||||
hook.Add("HUDPaint", "whBoneIndicator", function()
|
||||
if WepHolster.lookingBone then
|
||||
for k, ply in pairs(player.GetAll()) do
|
||||
lp = LocalPlayer()
|
||||
local bone = ply:LookupBone(WepHolster.lookingBone)
|
||||
local matrix = ply:GetBoneMatrix(bone)
|
||||
|
||||
if not matrix then
|
||||
return
|
||||
end
|
||||
|
||||
local pos = matrix:GetTranslation()
|
||||
pos = pos:ToScreen()
|
||||
local wihe = 6
|
||||
draw.RoundedBox(2, pos.x - wihe / 2, pos.y - wihe / 2, wihe, wihe, Color(0, 0, 0, 200))
|
||||
wihe = wihe - 2
|
||||
draw.RoundedBox(2, pos.x - wihe / 2, pos.y - wihe / 2, wihe, wihe, Color(255, 255, 255, 255))
|
||||
end
|
||||
end
|
||||
end)
|
||||
2043
addons/weapon_holsters/lua/autorun/server/sv_default_wepholster.lua
Normal file
2043
addons/weapon_holsters/lua/autorun/server/sv_default_wepholster.lua
Normal file
File diff suppressed because it is too large
Load Diff
207
addons/weapon_holsters/lua/autorun/server/sv_weapon_holsters.lua
Normal file
207
addons/weapon_holsters/lua/autorun/server/sv_weapon_holsters.lua
Normal file
@@ -0,0 +1,207 @@
|
||||
--[[
|
||||
| This file was obtained through the combined efforts
|
||||
| of Madbluntz & Plymouth Antiquarian Society.
|
||||
|
|
||||
| Credits: lifestorm, Gregory Wayne Rossel JR.,
|
||||
| Maloy, DrPepper10 @ RIP, Atle!
|
||||
|
|
||||
| Visit for more: https://plymouth.thetwilightzone.ru/
|
||||
--]]
|
||||
|
||||
--[[
|
||||
__ ___ __ __
|
||||
/ |/ /__ ____/ /__ / / __ __
|
||||
/ /|_/ / _ `/ _ / -_) / _ \/ // /
|
||||
/_/ /_/\_,_/\_,_/\__/ /_.__/\_, /
|
||||
___ __ /___/ ___ __
|
||||
/ _ \___ / /_ _____ ___ / /____ ____ / _ \__ ______/ /__
|
||||
/ ___/ _ \/ / // / -_|_-</ __/ -_) __/ / // / // / __/ '_/
|
||||
/_/ \___/_/\_, /\__/___/\__/\__/_/ /____/\_,_/\__/_/\_\
|
||||
/___/
|
||||
https://steamcommunity.com/profiles/76561198057599363
|
||||
]]
|
||||
WepHolster.wepInfo = WepHolster.wepInfo or {}
|
||||
util.AddNetworkString("sendWHData")
|
||||
util.AddNetworkString("sendWholeWHData")
|
||||
util.AddNetworkString("applyWepHolsterData")
|
||||
util.AddNetworkString("reloadWH")
|
||||
util.AddNetworkString("deleteWHData")
|
||||
util.AddNetworkString("reloadWholeWH")
|
||||
util.AddNetworkString("resetWHDataToDefault")
|
||||
util.AddNetworkString("resetWholeWHDataToDefault")
|
||||
util.AddNetworkString("WepHolsters_Settings")
|
||||
|
||||
function WepHolster.setWHData(wep, tbl)
|
||||
file.Write("wepholster/" .. wep .. ".txt", util.TableToJSON(tbl, true))
|
||||
WepHolster.wepInfo[wep] = tbl
|
||||
end
|
||||
|
||||
--[[
|
||||
local function InitOfInit()
|
||||
for k, v in pairs(WepHolster.defData) do
|
||||
WepHolster.setWHData(k, v)
|
||||
end
|
||||
end
|
||||
hook.Add("Initialize", "wepHolstersInit", function()
|
||||
if file.IsDir("wepholster", "DATA") then
|
||||
local files, dirs = file.Find("wepholster/*.txt", "DATA")
|
||||
|
||||
for k, v in pairs(files) do
|
||||
WepHolster.wepInfo[string.sub(v, 1, #v - 4)] = util.JSONToTable(file.Read("wepholster/" .. v))
|
||||
end
|
||||
else
|
||||
file.CreateDir("wepholster", "DATA")
|
||||
InitOfInit()
|
||||
end
|
||||
end)
|
||||
]]
|
||||
local function checkValidSWEP()
|
||||
if not file.IsDir("wepholster", "DATA") then
|
||||
file.CreateDir("wepholster", "DATA")
|
||||
|
||||
for k, v in pairs(WepHolster.defData) do
|
||||
file.Write("wepholster/" .. k .. ".txt", util.TableToJSON(v, true))
|
||||
end
|
||||
end
|
||||
|
||||
local files, dirs = file.Find("wepholster/*.txt", "DATA")
|
||||
|
||||
for k, v in pairs(files) do
|
||||
local wepclass = string.sub(v, 1, #v - 4)
|
||||
local swep = weapons.Get(wepclass)
|
||||
|
||||
if swep or WepHolster.HL2Weps[wepclass] or not WepHolster.defData[wepclass] then
|
||||
WepHolster.wepInfo[wepclass] = util.JSONToTable(file.Read("wepholster/" .. v))
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
hook.Add("Initialize", "Initialize Weapon Holsters", checkValidSWEP)
|
||||
|
||||
function WepHolster.sendWholeWHData(ply)
|
||||
net.Start("sendWholeWHData")
|
||||
net.WriteTable(WepHolster.wepInfo)
|
||||
net.Send(ply)
|
||||
end
|
||||
|
||||
hook.Add("PlayerInitialSpawn", "sendWholeWHData", WepHolster.sendWholeWHData)
|
||||
|
||||
net.Receive("resetWholeWHDataToDefault", function(len, ply)
|
||||
if ply:IsSuperAdmin() then
|
||||
local files, dirs = file.Find("wepholster/*", "DATA")
|
||||
|
||||
for k, v in pairs(files) do
|
||||
file.Delete("wepholster/" .. v)
|
||||
--print(v)
|
||||
end
|
||||
file.Delete("wepholster")
|
||||
WepHolster.wepInfo = {}
|
||||
checkValidSWEP()
|
||||
net.Start("sendWholeWHData")
|
||||
net.WriteTable(WepHolster.wepInfo)
|
||||
net.Broadcast()
|
||||
end
|
||||
end)
|
||||
|
||||
net.Receive("resetWHDataToDefault", function(len, ply)
|
||||
if ply:IsSuperAdmin() then
|
||||
local class = net.ReadString()
|
||||
|
||||
if WepHolster.defData[class] then
|
||||
net.Start("sendWHData")
|
||||
net.WriteString(class)
|
||||
net.WriteTable(WepHolster.defData[class])
|
||||
net.Send(ply)
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
||||
net.Receive("reloadWholeWH", function(len, ply)
|
||||
WepHolster.sendWholeWHData(ply)
|
||||
end)
|
||||
|
||||
net.Receive("applyWepHolsterData", function(len, ply)
|
||||
if ply:IsSuperAdmin() then
|
||||
local class = net.ReadString()
|
||||
local weptbl = net.ReadTable()
|
||||
weptbl.notSavedYet = nil
|
||||
weptbl.isEditing = nil
|
||||
WepHolster.setWHData(class, weptbl)
|
||||
net.Start("sendWHData")
|
||||
net.WriteString(class)
|
||||
net.WriteTable(WepHolster.wepInfo[class])
|
||||
net.Broadcast()
|
||||
end
|
||||
end)
|
||||
|
||||
net.Receive("reloadWH", function(len, ply)
|
||||
if ply:IsSuperAdmin() then
|
||||
local class = net.ReadString()
|
||||
|
||||
if WepHolster.wepInfo[class] then
|
||||
net.Start("sendWHData")
|
||||
net.WriteString(class)
|
||||
net.WriteTable(WepHolster.wepInfo[class])
|
||||
net.Send(ply)
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
||||
net.Receive("deleteWHData", function(len, ply)
|
||||
if ply:IsSuperAdmin() then
|
||||
local class = net.ReadString()
|
||||
WepHolster.wepInfo[class] = nil
|
||||
|
||||
if file.Exists("wepholster/" .. class .. ".txt", "DATA") then
|
||||
file.Delete("wepholster/" .. class .. ".txt")
|
||||
end
|
||||
|
||||
net.Start("sendWHData")
|
||||
net.WriteString(class)
|
||||
net.WriteTable({})
|
||||
net.Broadcast()
|
||||
end
|
||||
end)
|
||||
|
||||
function WepHolster.CanEditSetting(ply, con, var)
|
||||
if not ply:IsSuperAdmin() then
|
||||
ply:PrintMessage(HUD_PRINTCENTER, "You don't have access to server settings.")
|
||||
|
||||
return
|
||||
end
|
||||
|
||||
if not ConVarExists(con) then
|
||||
return
|
||||
end
|
||||
|
||||
print("[Weapon Holsters] " .. ply:Nick() .. " (" .. ply:SteamID() .. ") changed " .. con .. " to " .. tostring(var))
|
||||
con = GetConVar(con)
|
||||
con:SetString(var)
|
||||
end
|
||||
|
||||
local whitelist = {}
|
||||
whitelist["sv_weapon_holsters"] = true
|
||||
|
||||
net.Receive("WepHolsters_Settings", function(len, ply)
|
||||
if not ply then
|
||||
return
|
||||
end
|
||||
|
||||
if (ply.WH_LAST or 0) > SysTime() then
|
||||
return
|
||||
end
|
||||
|
||||
ply.WH_LAST = SysTime() + 0.2
|
||||
local con = net.ReadString()
|
||||
local arg = net.ReadString()
|
||||
|
||||
if not con then
|
||||
return
|
||||
end
|
||||
|
||||
if not whitelist[con] then
|
||||
return
|
||||
end
|
||||
|
||||
WepHolster.CanEditSetting(ply, con, arg or nil)
|
||||
end)
|
||||
29
addons/weapon_holsters/lua/autorun/sh_weapon_holsters.lua
Normal file
29
addons/weapon_holsters/lua/autorun/sh_weapon_holsters.lua
Normal file
@@ -0,0 +1,29 @@
|
||||
--[[
|
||||
| This file was obtained through the combined efforts
|
||||
| of Madbluntz & Plymouth Antiquarian Society.
|
||||
|
|
||||
| Credits: lifestorm, Gregory Wayne Rossel JR.,
|
||||
| Maloy, DrPepper10 @ RIP, Atle!
|
||||
|
|
||||
| Visit for more: https://plymouth.thetwilightzone.ru/
|
||||
--]]
|
||||
|
||||
if not ConVarExists("sv_weapon_holsters") then
|
||||
CreateConVar("sv_weapon_holsters",1, { FCVAR_REPLICATED, FCVAR_ARCHIVE,FCVAR_SERVER_CAN_EXECUTE }, "Enable Weapon Holsters (server side)" )
|
||||
end
|
||||
WepHolster = WepHolster or {}
|
||||
WepHolster.HL2Weps = {
|
||||
["weapon_pistol"] = "Pistol",
|
||||
["weapon_357"] = "357",
|
||||
["weapon_frag"] = "Frag Grenade",
|
||||
["weapon_slam"] = "SLAM",
|
||||
["weapon_crowbar"] = "Crowbar",
|
||||
["weapon_stunstick"] = "Stunstick",
|
||||
["weapon_shotgun"] = "Shotgun",
|
||||
["weapon_rpg"] = "RPG Launcher",
|
||||
["weapon_smg1"] = "SMG",
|
||||
["weapon_ar2"] = "AR2",
|
||||
["weapon_crossbow"] = "Crossbow",
|
||||
["weapon_physcannon"] = "Gravity Gun",
|
||||
["weapon_physgun"] = "Physics Gun"
|
||||
}
|
||||
Reference in New Issue
Block a user