Files
wnsrc/lua/entities/widget_bones.lua
lifestorm 6a58f406b1 Upload
2024-08-04 23:54:45 +03:00

181 lines
3.9 KiB
Lua

--[[
| 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/
--]]
AddCSLuaFile()
local matBone = Material( "widgets/bone.png", "smooth" )
local matBoneSmall = Material( "widgets/bone_small.png", "smooth" )
local widget_bone = {
Base = "widget_base",
a = 255,
GetParentPos = function( self )
local p = self:GetParent()
if ( !IsValid( p ) ) then return end
local bp = p:GetBoneParent( self:GetParentAttachment() )
if ( bp <= 0 ) then return end
return p:GetBonePosition( bp )
end,
OverlayRender = function( self )
local pp = self:GetParentPos()
if ( !pp ) then return end
--local fwd = self:GetAngles():Forward()
local len = self:GetSize() / 2
local w = len * 0.2
if ( len > 10 ) then
render.SetMaterial( matBone )
else
render.SetMaterial( matBoneSmall )
end
local c = Color( 255, 255, 255, 255 )
if ( self:IsHovered() ) then
self.a = math.Approach( self.a, 255, FrameTime() * 255 * 10 )
elseif ( self:SomethingHovered() ) then
self.a = math.Approach( self.a, 20, FrameTime() * 255 * 10 )
else
self.a = math.Approach( self.a, 255, FrameTime() * 255 * 10 )
end
cam.IgnoreZ( true )
render.DrawBeam( self:GetPos(), pp, w, 0, 1, Color( c.r, c.g, c.b, self.a * 0.5 ) )
cam.IgnoreZ( false )
render.DrawBeam( self:GetPos(), pp, w, 0, 1, Color( c.r, c.g, c.b, self.a ) )
end,
TestCollision = function( self, startpos, delta, isbox, extents )
if ( isbox ) then return end
if ( !widgets.Tracing ) then return end
local pp = self:GetParentPos()
if ( !pp ) then return end
local fwd = ( pp - self:GetPos() ):GetNormal()
local ang = fwd:Angle()
local len = self:GetSize() / 2
local w = len * 0.2
local mins = Vector( 0, w * -0.5, w * -0.5 )
local maxs = Vector( len, w * 0.5, w * 0.5 )
local hit, norm, fraction = util.IntersectRayWithOBB( startpos, delta, self:GetPos(), ang, mins, maxs )
if ( !hit ) then return end
--debugoverlay.BoxAngles( self:GetPos(), mins, maxs, ang, 0.1, Color( 0, 255, 0, 64 ) )
return {
HitPos = hit,
Fraction = fraction * self:GetPriority()
}
end,
Think = function( self )
if ( !SERVER ) then return end
if ( !IsValid( self:GetParent() ) ) then return end
--
-- Because the bone length changes (with the manipulator)
-- we need to update the bones pretty regularly
--
local size = self:GetParent():BoneLength( self:GetParentAttachment() ) * 2
size = math.ceil( size )
self:SetSize( size )
end,
CalcAbsolutePosition = function( self, v, a )
local ent = self:GetParent()
if ( !IsValid( ent ) ) then return end
local bone = self:GetParentAttachment()
if ( bone <= 0 ) then return end
return ent:GetBonePosition( bone )
end
}
scripted_ents.Register( widget_bone, "widget_bone" )
DEFINE_BASECLASS( "widget_base" )
function ENT:SetupDataTables()
self:NetworkVar( "Entity", 0, "Target" )
self.BaseClass.SetupDataTables( self )
end
--
-- Set our dimensions etc
--
function ENT:Initialize()
self.BaseClass.Initialize( self )
self:SetCollisionBounds( Vector( -1, -1, -1 ), Vector( 1, 1, 1 ) )
self:SetSolid( SOLID_NONE )
end
function ENT:Setup( ent )
self:SetTarget( ent )
self:SetParent( ent )
self:SetLocalPos( vector_origin )
for k = 0, ent:GetBoneCount() - 1 do
if ( ent:GetBoneParent( k ) <= 0 ) then continue end
if ( !ent:BoneHasFlag( k, BONE_USED_BY_VERTEX_LOD0 ) ) then continue end
local btn = ents.Create( "widget_bone" )
btn:FollowBone( ent, k )
btn:SetLocalPos( vector_origin )
btn:SetLocalAngles( angle_zero )
btn:Spawn()
btn:SetSize( ent:BoneLength( k ) * 2 )
btn.OnClick = function( x, ply )
self:OnBoneClick( k, ply )
end
self:DeleteOnRemove( btn )
end
end
function ENT:OnBoneClick( boneid, ply )
end
function ENT:OverlayRender()
end