· 6 years ago · Apr 13, 2019, 03:58 AM
1CreateConVar( "lordi_sledge_break_doors", "1", { FCVAR_REPLICATED, FCVAR_NOTIFY }, "Should people be able to break down doors using the sledgehammer? 1 for true, 0 for false" )
2CreateConVar( "lordi_sledge_break_doors_chance", "5", { FCVAR_REPLICATED, FCVAR_NOTIFY }, "What should the 1/<command> chance be before a door breaks? The higher this is, the harder it is. 1 makes it break immediadly" )
3
4SWEP.WElements = {
5 ["sledge"] = { type = "Model", model = "models/weapons/lordi/c_sledgehammer.mdl", bone = "ValveBiped.Bip01_R_Hand", rel = "", pos = Vector(-16.33, -3.294, -16.605), angle = Angle(8.395, 0, -115.988), size = Vector(1, 1, 1), color = Color(255, 255, 255, 255), surpresslightning = false, material = "", skin = 0, bodygroup = {} }
6}
7
8SWEP.ViewModelFOV = 70
9SWEP.ViewModel = "models/weapons/lordi/c_sledgehammer.mdl"
10SWEP.WorldModel = "models/weapons/w_crowbar.mdl"
11SWEP.UseHands = true
12SWEP.AutoSwitchTo = true
13SWEP.Slot = 0
14SWEP.HoldType = "passive"
15SWEP.Spawnable = true
16SWEP.AdminSpawnable = false
17SWEP.DrawCrosshair = false
18SWEP.Category = "LordiAnders's Weapons"
19SWEP.SlotPos = 0
20SWEP.DrawAmmo = true
21SWEP.PrintName = "Sledgehammer"
22SWEP.Author = "LordiAnders"
23SWEP.Instructions = "Bash heads in! Or if they are afar, throw the thing after them!"
24SWEP.ShowViewModel = true
25SWEP.ShowWorldModel = true
26
27SWEP.Primary.ClipSize = -1
28SWEP.Primary.DefaultClip = -1
29SWEP.Primary.Ammo = "none"
30SWEP.Primary.Automatic = true
31
32SWEP.Secondary.ClipSize = -1
33SWEP.Secondary.Ammo = "none"
34SWEP.Secondary.Automatic = true
35
36SWEP.AboutToSwing = false
37SWEP.IsSwinging = false
38
39SWEP.AboutToSwing2 = false
40SWEP.IsSwinging2 = false
41
42if CLIENT then
43 SWEP.WepSelectIcon = surface.GetTextureID("vgui/entities/weapon_lordi_sledgehammer")
44 killicon.Add("weapon_lordi_sledgehammer","vgui/entities/weapon_lordi_sledgehammer",Color(255,255,255,255))
45 killicon.Add("ent_lordi_sledgehammer","vgui/entities/weapon_lordi_sledgehammer",Color(255,255,255,255))
46 SWEP.BounceWeaponIcon = false
47end
48
49function SWEP:VerifyAndSet(bone,data)
50 if not IsValid(self.Owner) then return end
51 local bone = self.Owner:LookupBone(bone)
52 if bone then
53 self.Owner:ManipulateBoneAngles(bone,data)
54 end
55end
56
57function SWEP:SetPassiveHoldType()
58 if not IsValid(self.Owner) then return end
59 if CLIENT then return end
60
61 self:SetHoldType("passive")
62
63 self:VerifyAndSet('ValveBiped.Bip01_R_UpperArm',Angle(13.8940719901227,12.334109775164,14.597405385818))
64 self:VerifyAndSet('ValveBiped.Bip01_R_Hand',Angle(17,30,9))
65 self:VerifyAndSet('ValveBiped.Bip01_L_Forearm',Angle(-16.224373259067,-24.886877720213,7.8929222269922))
66 self:VerifyAndSet('ValveBiped.Bip01_L_UpperArm',Angle(-32.017127057138,-35.637168682527,16))
67 self:VerifyAndSet('ValveBiped.Bip01_L_Hand',Angle(0.17154435310358,0,0))
68end
69
70function SWEP:SetMelee2HoldType()
71 if not IsValid(self.Owner) then return end
72 if CLIENT then return end
73
74 self:SetHoldType("melee2")
75
76 self:VerifyAndSet('ValveBiped.Bip01_R_UpperArm',Angle(0,0,0))
77 self:VerifyAndSet('ValveBiped.Bip01_R_Hand',Angle(0,0,0))
78 self:VerifyAndSet('ValveBiped.Bip01_L_Forearm',Angle(0,0,0))
79 self:VerifyAndSet('ValveBiped.Bip01_L_UpperArm',Angle(0,0,0))
80 self:VerifyAndSet('ValveBiped.Bip01_L_Hand',Angle(0,0,0))
81end
82
83function SWEP:Deploy()
84self.Weapon:SendWeaponAnim(ACT_VM_DRAW)
85self:SetDeploySpeed(self.Owner:GetViewModel():SequenceDuration())
86self.Weapon:SetNextPrimaryFire( CurTime() + self.Owner:GetViewModel():SequenceDuration() )
87self.Weapon:SetNextSecondaryFire( CurTime() + self.Owner:GetViewModel():SequenceDuration() )
88
89self.AboutToSwing = true --Just to disable holstering
90
91self:SetPassiveHoldType()
92
93if SERVER then
94 timer.Simple(0.9,function()
95 if not self:IsValid() then return end
96 self:EmitSound("npc/combine_soldier/gear6.wav")
97 self.Owner:ViewPunch( Angle(-2,0,1) )
98 end)
99 timer.Simple(2,function()
100 if not self:IsValid() then return end
101 self.Owner:ViewPunch( Angle(5,0,-5) )
102 self:EmitSound("physics/flesh/flesh_impact_hard2.wav",75,180)
103 self.AboutToSwing = false
104 end)
105end
106end
107
108function SWEP:Think()
109 if self.IsSwinging and not self.Owner:KeyDown(IN_ATTACK) then
110 self:PrimaryAttack()
111 elseif self.IsSwinging2 and not self.Owner:KeyDown(IN_ATTACK2) then
112 self:SecondaryAttack()
113 end
114end
115
116function SWEP:PrimaryAttack()
117 if self.IsSwinging2 or self.AboutToSwing2 then return end
118 if not self.IsSwinging then
119 self.AboutToSwing = true
120 self:SetMelee2HoldType()
121 self.Weapon:SetNextPrimaryFire( CurTime() + 5000 )
122 self.Weapon:SendWeaponAnim(ACT_VM_PRIMARYATTACK)
123 timer.Simple(self.Owner:GetViewModel():SequenceDuration(),function()
124 self.AboutToSwing = false
125 self.IsSwinging = true
126 end)
127 end
128
129 if self.IsSwinging then
130 --Trace shit from weapon_fists.lua packed with Gmod
131 self.Owner:SetAnimation( PLAYER_ATTACK1 )
132 timer.Simple(0.25,function() if not self:IsValid() then return end self:SetPassiveHoldType() end)
133 local trace = util.TraceLine( {
134 start = self.Owner:GetShootPos(),
135 endpos = self.Owner:GetShootPos() + self.Owner:GetAimVector() * 105,
136 filter = self.Owner
137 } )
138
139 if ( !IsValid( trace.Entity ) ) then
140 trace = util.TraceHull( {
141 start = self.Owner:GetShootPos(),
142 endpos = self.Owner:GetShootPos() + self.Owner:GetAimVector() * 105,
143 filter = self.Owner,
144 mins = Vector( -10, -10, -8 ),
145 maxs = Vector( 10, 10, 8 )
146 } )
147 end
148
149 if trace.Entity:IsValid() or trace.HitWorld then
150 self.Weapon:SendWeaponAnim(ACT_VM_HITKILL)
151 self.Owner:ViewPunch( Angle(-10,0,0) )
152 timer.Simple(0.1,function()
153 if not self:IsValid() then return end
154 self.Owner:ViewPunch( Angle(15,0,0) )
155 end)
156 if trace.Entity:IsValid() then
157 if trace.Entity:IsPlayer() or trace.Entity:IsNPC() then
158 if SERVER then trace.Entity:EmitSound("physics/body/body_medium_break"..math.random(2,4)..".wav",75,math.random(70,90)) end
159 local effectdata = EffectData()
160 effectdata:SetOrigin(trace.HitPos)
161 effectdata:SetEntity(trace.Entity)
162 util.Effect( "BloodImpact", effectdata )
163 elseif trace.Entity:GetClass() == "prop_door_rotating" and GetConVarNumber( "lordi_sledge_break_doors" ) == 1 then
164 if SERVER and math.random(1,GetConVarNumber( "lordi_sledge_break_doors_chance" )) == 1 then
165 trace.Entity:Fire("unlock")
166 trace.Entity:Fire("open")
167
168 trace.Entity:SetNotSolid(true)
169 trace.Entity:SetNoDraw(true)
170
171 --Bit of madcow stuff here... :L
172
173 local ent = ents.Create("prop_physics")
174
175 trace.Entity:EmitSound("physics/wood/wood_furniture_break1.wav")
176
177 ent:SetPos(trace.Entity:GetPos())
178 ent:SetAngles(trace.Entity:GetAngles())
179 ent:SetModel(trace.Entity:GetModel())
180
181 if trace.Entity:GetSkin() then
182 ent:SetSkin(trace.Entity:GetSkin())
183 end
184
185 ent:Spawn()
186
187 ent:GetPhysicsObject():ApplyForceCenter( self.Owner:GetAimVector() * 10000 )
188
189 timer.Simple(25,function()
190 if ent:IsValid() then
191 ent:Remove()
192 end
193 trace.Entity:SetNotSolid(false)
194 trace.Entity:SetNoDraw(false)
195 end)
196 elseif SERVER then
197 trace.Entity:EmitSound("physics/wood/wood_box_break"..math.random(1,2)..".wav",75,math.random(50,150))
198 end
199 end
200 if SERVER then trace.Entity:TakeDamage(math.random(70,120),self.Owner) end
201 end
202 if trace.HitWorld then
203 local trace = self.Owner:GetEyeTrace()
204
205 if self.Owner:GetShootPos():Distance(trace.HitPos) <= 105 then
206 util.Decal("Impact.Sand",trace.HitPos + trace.HitNormal,trace.HitPos - trace.HitNormal)
207 end
208 end
209 if SERVER then timer.Simple(0,function() if not self:IsValid() then return end self:EmitSound("physics/metal/metal_canister_impact_hard"..math.random(1,3)..".wav",75,math.random(90,110)) end) end
210 else
211 self.Weapon:SendWeaponAnim(ACT_VM_MISSCENTER)
212 if SERVER then timer.Simple(0,function() if not self:IsValid() then return end self:EmitSound("npc/zombie/claw_miss1.wav",75,60) end) end
213 self.Owner:ViewPunch( Angle(-10,0,0) )
214 timer.Simple(0.1,function()
215 if not self:IsValid() then return end
216 self.Owner:ViewPunch( Angle(30,0,0) )
217 end)
218 end
219 self.IsSwinging = false
220 self.Weapon:SetNextPrimaryFire( CurTime() + 1 )
221 self.Weapon:SetNextSecondaryFire( CurTime() + 1 )
222 end
223end
224
225function SWEP:GetViewModelPosition(pos, ang)
226 if self.IsSwinging then
227 pos = pos + (math.random(-1,1) / 40) * ang:Right()
228 pos = pos + (math.random(-1,1) / 40) * ang:Forward()
229 pos = pos + (math.random(-1,1) / 40) * ang:Up()
230 end
231
232 return pos, ang
233end
234
235function SWEP:SecondaryAttack()
236 if self.IsSwinging or self.AboutToSwing then return end
237 if not self.IsSwinging2 then
238 self.AboutToSwing2 = true
239 self:SetMelee2HoldType()
240 self.Weapon:SetNextSecondaryFire( CurTime() + 5000 )
241 self.Weapon:SendWeaponAnim(ACT_VM_PRIMARYATTACK)
242 timer.Simple(self.Owner:GetViewModel():SequenceDuration(),function()
243 self.AboutToSwing2 = false
244 self.IsSwinging2 = true
245 end)
246 end
247
248 if self.IsSwinging2 then
249 self.IsSwinging2 = false
250 self.Weapon:SendWeaponAnim(ACT_VM_MISSCENTER)
251 timer.Simple(0.1,function()
252 if SERVER then
253 local sledge = ents.Create("ent_lordi_sledgehammer")
254 sledge:SetOwner(self.Owner)
255 sledge:SetPos(self.Owner:EyePos() + self.Owner:GetAimVector())
256 sledge:SetAngles(self.Owner:GetAngles())
257 sledge:Spawn()
258 sledge:Activate()
259
260 sledge:GetPhysicsObject():ApplyForceCenter( self.Owner:GetAimVector() * 7000 )
261
262 timer.Simple(0.25,function() self.Owner:StripWeapon(self:GetClass()) end)
263 end
264 end)
265 end
266end
267
268function SWEP:Reload() end
269
270function SWEP:OnRemove()
271 if IsValid(self.Owner) then
272 self:VerifyAndSet('ValveBiped.Bip01_R_UpperArm',Angle(0,0,0))
273 self:VerifyAndSet('ValveBiped.Bip01_R_Hand',Angle(0,0,0))
274 self:VerifyAndSet('ValveBiped.Bip01_L_Forearm',Angle(0,0,0))
275 self:VerifyAndSet('ValveBiped.Bip01_L_UpperArm',Angle(0,0,0))
276 self:VerifyAndSet('ValveBiped.Bip01_L_Hand',Angle(0,0,0))
277 local vm = self.Owner:GetViewModel()
278 if IsValid(vm) then vm:SetMaterial("") end
279 end
280 if CLIENT and IsValid(self.Owner) then
281 local vm = self.Owner:GetViewModel()
282 if IsValid(vm) then
283 self:ResetBonePositions(vm)
284 end
285 end
286end
287
288/********************************************************
289 SWEP Construction Kit base code
290 Created by Clavus
291 Available for public use, thread at:
292 facepunch.com/threads/1032378
293
294
295 DESCRIPTION:
296 This script is meant for experienced scripters
297 that KNOW WHAT THEY ARE DOING. Don't come to me
298 with basic Lua questions.
299
300 Just copy into your SWEP or SWEP base of choice
301 and merge with your own code.
302
303 The SWEP.VElements, SWEP.WElements and
304 SWEP.ViewModelBoneMods tables are all optional
305 and only have to be visible to the client.
306********************************************************/
307
308function SWEP:Initialize()
309 self:SetHoldType(self.HoldType)
310
311 // other initialize code goes here
312
313 if CLIENT then
314
315 // Create a new table for every weapon instance
316 self.VElements = table.FullCopy( self.VElements )
317 self.WElements = table.FullCopy( self.WElements )
318 self.ViewModelBoneMods = table.FullCopy( self.ViewModelBoneMods )
319
320 self:CreateModels(self.VElements) // create viewmodels
321 self:CreateModels(self.WElements) // create worldmodels
322
323 // init view model bone build function
324 if IsValid(self.Owner) then
325 local vm = self.Owner:GetViewModel()
326 if IsValid(vm) then
327 self:ResetBonePositions(vm)
328 end
329
330 // Init viewmodel visibility
331 end
332
333 end
334
335end
336
337function SWEP:Holster()
338
339 if self.AboutToSwing or self.IsSwinging or self.IsSwinging2 or self.AboutToSwing2 then return end
340
341 self:OnRemove()
342
343 if CLIENT and IsValid(self.Owner) then
344 local vm = self.Owner:GetViewModel()
345 if IsValid(vm) then
346 self:ResetBonePositions(vm)
347 end
348 end
349
350 return true
351end
352
353if CLIENT then
354
355 SWEP.vRenderOrder = nil
356 function SWEP:ViewModelDrawn()
357
358 local vm = self.Owner:GetViewModel()
359 if !IsValid(vm) then return end
360
361 if (!self.VElements) then return end
362
363 self:UpdateBonePositions(vm)
364
365 if (!self.vRenderOrder) then
366
367 // we build a render order because sprites need to be drawn after models
368 self.vRenderOrder = {}
369
370 for k, v in pairs( self.VElements ) do
371 if (v.type == "Model") then
372 table.insert(self.vRenderOrder, 1, k)
373 elseif (v.type == "Sprite" or v.type == "Quad") then
374 table.insert(self.vRenderOrder, k)
375 end
376 end
377
378 end
379
380 for k, name in ipairs( self.vRenderOrder ) do
381
382 local v = self.VElements[name]
383 if (!v) then self.vRenderOrder = nil break end
384 if (v.hide) then continue end
385
386 local model = v.modelEnt
387 local sprite = v.spriteMaterial
388
389 if (!v.bone) then continue end
390
391 local pos, ang = self:GetBoneOrientation( self.VElements, v, vm )
392
393 if (!pos) then continue end
394
395 if (v.type == "Model" and IsValid(model)) then
396
397 model:SetPos(pos + ang:Forward() * v.pos.x + ang:Right() * v.pos.y + ang:Up() * v.pos.z )
398 ang:RotateAroundAxis(ang:Up(), v.angle.y)
399 ang:RotateAroundAxis(ang:Right(), v.angle.p)
400 ang:RotateAroundAxis(ang:Forward(), v.angle.r)
401
402 model:SetAngles(ang)
403 //model:SetModelScale(v.size)
404 local matrix = Matrix()
405 matrix:Scale(v.size)
406 model:EnableMatrix( "RenderMultiply", matrix )
407
408 if (v.material == "") then
409 model:SetMaterial("")
410 elseif (model:GetMaterial() != v.material) then
411 model:SetMaterial( v.material )
412 end
413
414 if (v.skin and v.skin != model:GetSkin()) then
415 model:SetSkin(v.skin)
416 end
417
418 if (v.bodygroup) then
419 for k, v in pairs( v.bodygroup ) do
420 if (model:GetBodygroup(k) != v) then
421 model:SetBodygroup(k, v)
422 end
423 end
424 end
425
426 if (v.surpresslightning) then
427 render.SuppressEngineLighting(true)
428 end
429
430 render.SetColorModulation(v.color.r/255, v.color.g/255, v.color.b/255)
431 render.SetBlend(v.color.a/255)
432 model:DrawModel()
433 render.SetBlend(1)
434 render.SetColorModulation(1, 1, 1)
435
436 if (v.surpresslightning) then
437 render.SuppressEngineLighting(false)
438 end
439
440 elseif (v.type == "Sprite" and sprite) then
441
442 local drawpos = pos + ang:Forward() * v.pos.x + ang:Right() * v.pos.y + ang:Up() * v.pos.z
443 render.SetMaterial(sprite)
444 render.DrawSprite(drawpos, v.size.x, v.size.y, v.color)
445
446 elseif (v.type == "Quad" and v.draw_func) then
447
448 local drawpos = pos + ang:Forward() * v.pos.x + ang:Right() * v.pos.y + ang:Up() * v.pos.z
449 ang:RotateAroundAxis(ang:Up(), v.angle.y)
450 ang:RotateAroundAxis(ang:Right(), v.angle.p)
451 ang:RotateAroundAxis(ang:Forward(), v.angle.r)
452
453 cam.Start3D2D(drawpos, ang, v.size)
454 v.draw_func( self )
455 cam.End3D2D()
456
457 end
458
459 end
460
461 end
462
463 SWEP.wRenderOrder = nil
464 function SWEP:DrawWorldModel()
465
466 self:DrawModel()
467 self:SetMaterial( "engine/occlusionproxy" )
468
469 if (!self.WElements) then return end
470
471 if (!self.wRenderOrder) then
472
473 self.wRenderOrder = {}
474
475 for k, v in pairs( self.WElements ) do
476 if (v.type == "Model") then
477 table.insert(self.wRenderOrder, 1, k)
478 elseif (v.type == "Sprite" or v.type == "Quad") then
479 table.insert(self.wRenderOrder, k)
480 end
481 end
482
483 end
484
485 if (IsValid(self.Owner)) then
486 bone_ent = self.Owner
487 else
488 // when the weapon is dropped
489 bone_ent = self
490 end
491
492 for k, name in pairs( self.wRenderOrder ) do
493
494 local v = self.WElements[name]
495 if (!v) then self.wRenderOrder = nil break end
496 if (v.hide) then continue end
497
498 local pos, ang
499
500 if (v.bone) then
501 pos, ang = self:GetBoneOrientation( self.WElements, v, bone_ent )
502 else
503 pos, ang = self:GetBoneOrientation( self.WElements, v, bone_ent, "ValveBiped.Bip01_R_Hand" )
504 end
505
506 if (!pos) then continue end
507
508 local model = v.modelEnt
509 local sprite = v.spriteMaterial
510
511 if (v.type == "Model" and IsValid(model)) then
512
513 model:SetPos(pos + ang:Forward() * v.pos.x + ang:Right() * v.pos.y + ang:Up() * v.pos.z )
514 ang:RotateAroundAxis(ang:Up(), v.angle.y)
515 ang:RotateAroundAxis(ang:Right(), v.angle.p)
516 ang:RotateAroundAxis(ang:Forward(), v.angle.r)
517
518 model:SetAngles(ang)
519 //model:SetModelScale(v.size)
520 local matrix = Matrix()
521 matrix:Scale(v.size)
522 model:EnableMatrix( "RenderMultiply", matrix )
523
524 if (v.material == "") then
525 model:SetMaterial("")
526 elseif (model:GetMaterial() != v.material) then
527 model:SetMaterial( v.material )
528 end
529
530 if (v.skin and v.skin != model:GetSkin()) then
531 model:SetSkin(v.skin)
532 end
533
534 if (v.bodygroup) then
535 for k, v in pairs( v.bodygroup ) do
536 if (model:GetBodygroup(k) != v) then
537 model:SetBodygroup(k, v)
538 end
539 end
540 end
541
542 if (v.surpresslightning) then
543 render.SuppressEngineLighting(true)
544 end
545
546 render.SetColorModulation(v.color.r/255, v.color.g/255, v.color.b/255)
547 render.SetBlend(v.color.a/255)
548 model:DrawModel()
549 render.SetBlend(1)
550 render.SetColorModulation(1, 1, 1)
551
552 if (v.surpresslightning) then
553 render.SuppressEngineLighting(false)
554 end
555
556 elseif (v.type == "Sprite" and sprite) then
557
558 local drawpos = pos + ang:Forward() * v.pos.x + ang:Right() * v.pos.y + ang:Up() * v.pos.z
559 render.SetMaterial(sprite)
560 render.DrawSprite(drawpos, v.size.x, v.size.y, v.color)
561
562 elseif (v.type == "Quad" and v.draw_func) then
563
564 local drawpos = pos + ang:Forward() * v.pos.x + ang:Right() * v.pos.y + ang:Up() * v.pos.z
565 ang:RotateAroundAxis(ang:Up(), v.angle.y)
566 ang:RotateAroundAxis(ang:Right(), v.angle.p)
567 ang:RotateAroundAxis(ang:Forward(), v.angle.r)
568
569 cam.Start3D2D(drawpos, ang, v.size)
570 v.draw_func( self )
571 cam.End3D2D()
572
573 end
574
575 end
576
577 end
578
579 function SWEP:GetBoneOrientation( basetab, tab, ent, bone_override )
580
581 local bone, pos, ang
582 if (tab.rel and tab.rel != "") then
583
584 local v = basetab[tab.rel]
585
586 if (!v) then return end
587
588 // Technically, if there exists an element with the same name as a bone
589 // you can get in an infinite loop. Let's just hope nobody's that stupid.
590 pos, ang = self:GetBoneOrientation( basetab, v, ent )
591
592 if (!pos) then return end
593
594 pos = pos + ang:Forward() * v.pos.x + ang:Right() * v.pos.y + ang:Up() * v.pos.z
595 ang:RotateAroundAxis(ang:Up(), v.angle.y)
596 ang:RotateAroundAxis(ang:Right(), v.angle.p)
597 ang:RotateAroundAxis(ang:Forward(), v.angle.r)
598
599 else
600
601 bone = ent:LookupBone(bone_override or tab.bone)
602
603 if (!bone) then return end
604
605 pos, ang = Vector(0,0,0), Angle(0,0,0)
606 local m = ent:GetBoneMatrix(bone)
607 if (m) then
608 pos, ang = m:GetTranslation(), m:GetAngles()
609 end
610
611 if (IsValid(self.Owner) and self.Owner:IsPlayer() and
612 ent == self.Owner:GetViewModel() and self.ViewModelFlip) then
613 ang.r = -ang.r // Fixes mirrored models
614 end
615
616 end
617
618 return pos, ang
619 end
620
621 function SWEP:CreateModels( tab )
622
623 if (!tab) then return end
624
625 // Create the clientside models here because Garry says we can't do it in the render hook
626 for k, v in pairs( tab ) do
627 if (v.type == "Model" and v.model and v.model != "" and (!IsValid(v.modelEnt) or v.createdModel != v.model) and
628 string.find(v.model, ".mdl") and file.Exists (v.model, "GAME") ) then
629
630 v.modelEnt = ClientsideModel(v.model, RENDER_GROUP_VIEW_MODEL_OPAQUE)
631 if (IsValid(v.modelEnt)) then
632 v.modelEnt:SetPos(self:GetPos())
633 v.modelEnt:SetAngles(self:GetAngles())
634 v.modelEnt:SetParent(self)
635 v.modelEnt:SetNoDraw(true)
636 v.createdModel = v.model
637 else
638 v.modelEnt = nil
639 end
640
641 elseif (v.type == "Sprite" and v.sprite and v.sprite != "" and (!v.spriteMaterial or v.createdSprite != v.sprite)
642 and file.Exists ("materials/"..v.sprite..".vmt", "GAME")) then
643
644 local name = v.sprite.."-"
645 local params = { ["$basetexture"] = v.sprite }
646 // make sure we create a unique name based on the selected options
647 local tocheck = { "nocull", "additive", "vertexalpha", "vertexcolor", "ignorez" }
648 for i, j in pairs( tocheck ) do
649 if (v[j]) then
650 params["$"..j] = 1
651 name = name.."1"
652 else
653 name = name.."0"
654 end
655 end
656
657 v.createdSprite = v.sprite
658 v.spriteMaterial = CreateMaterial(name,"UnlitGeneric",params)
659
660 end
661 end
662
663 end
664
665 local allbones
666 local hasGarryFixedBoneScalingYet = false
667
668 function SWEP:UpdateBonePositions2(vm)
669
670 if self.GrenadeThrowBoneMods then
671
672 if (!vm:GetBoneCount()) then return end
673
674 local loopthrough = self.GrenadeThrowBoneMods
675 if (!hasGarryFixedBoneScalingYet) then
676 allbones = {}
677 for i=0, vm:GetBoneCount() do
678 local bonename = vm:GetBoneName(i)
679 if (self.GrenadeThrowBoneMods[bonename]) then
680 allbones[bonename] = self.GrenadeThrowBoneMods[bonename]
681 else
682 allbones[bonename] = {
683 scale = Vector(1,1,1),
684 pos = Vector(0,0,0),
685 angle = Angle(0,0,0)
686 }
687 end
688 end
689
690 loopthrough = allbones
691 end
692
693 for k, v in pairs( loopthrough ) do
694 local bone = vm:LookupBone(k)
695 if (!bone) then continue end
696
697 local s = Vector(v.scale.x,v.scale.y,v.scale.z)
698 local p = Vector(v.pos.x,v.pos.y,v.pos.z)
699 local ms = Vector(1,1,1)
700 if (!hasGarryFixedBoneScalingYet) then
701 local cur = vm:GetBoneParent(bone)
702 while(cur >= 0) do
703 local pscale = loopthrough[vm:GetBoneName(cur)].scale
704 ms = ms * pscale
705 cur = vm:GetBoneParent(cur)
706 end
707 end
708
709 s = s * ms
710
711 if vm:GetManipulateBoneScale(bone) != s then
712 vm:ManipulateBoneScale( bone, s )
713 end
714 if vm:GetManipulateBoneAngles(bone) != v.angle then
715 vm:ManipulateBoneAngles( bone, v.angle )
716 end
717 if vm:GetManipulateBonePosition(bone) != p then
718 vm:ManipulateBonePosition( bone, p )
719 end
720 end
721 else
722 self:ResetBonePositions(vm)
723 end
724
725 end
726
727 function SWEP:UpdateBonePositions(vm)
728
729 if self.ViewModelBoneMods then
730
731 if (!vm:GetBoneCount()) then return end
732
733 // !! WORKAROUND !! //
734 // We need to check all model names :/
735 local loopthrough = self.ViewModelBoneMods
736 if (!hasGarryFixedBoneScalingYet) then
737 allbones = {}
738 for i=0, vm:GetBoneCount() do
739 local bonename = vm:GetBoneName(i)
740 if (self.ViewModelBoneMods[bonename]) then
741 allbones[bonename] = self.ViewModelBoneMods[bonename]
742 else
743 allbones[bonename] = {
744 scale = Vector(1,1,1),
745 pos = Vector(0,0,0),
746 angle = Angle(0,0,0)
747 }
748 end
749 end
750
751 loopthrough = allbones
752 end
753 // !! ----------- !! //
754
755 for k, v in pairs( loopthrough ) do
756 local bone = vm:LookupBone(k)
757 if (!bone) then continue end
758
759 // !! WORKAROUND !! //
760 local s = Vector(v.scale.x,v.scale.y,v.scale.z)
761 local p = Vector(v.pos.x,v.pos.y,v.pos.z)
762 local ms = Vector(1,1,1)
763 if (!hasGarryFixedBoneScalingYet) then
764 local cur = vm:GetBoneParent(bone)
765 while(cur >= 0) do
766 local pscale = loopthrough[vm:GetBoneName(cur)].scale
767 ms = ms * pscale
768 cur = vm:GetBoneParent(cur)
769 end
770 end
771
772 s = s * ms
773 // !! ----------- !! //
774
775 if vm:GetManipulateBoneScale(bone) != s then
776 vm:ManipulateBoneScale( bone, s )
777 end
778 if vm:GetManipulateBoneAngles(bone) != v.angle then
779 vm:ManipulateBoneAngles( bone, v.angle )
780 end
781 if vm:GetManipulateBonePosition(bone) != p then
782 vm:ManipulateBonePosition( bone, p )
783 end
784 end
785 else
786 self:ResetBonePositions(vm)
787 end
788
789 end
790
791 function SWEP:ResetBonePositions(vm)
792
793 if (!vm:GetBoneCount()) then return end
794 for i=0, vm:GetBoneCount() do
795 vm:ManipulateBoneScale( i, Vector(1, 1, 1) )
796 vm:ManipulateBoneAngles( i, Angle(0, 0, 0) )
797 vm:ManipulateBonePosition( i, Vector(0, 0, 0) )
798 end
799
800 end
801
802 /**************************
803 Global utility code
804 **************************/
805
806 // Fully copies the table, meaning all tables inside this table are copied too and so on (normal table.Copy copies only their reference).
807 // Does not copy entities of course, only copies their reference.
808 // WARNING: do not use on tables that contain themselves somewhere down the line or you'll get an infinite loop
809 function table.FullCopy( tab )
810
811 if (!tab) then return nil end
812
813 local res = {}
814 for k, v in pairs( tab ) do
815 if (type(v) == "table") then
816 res[k] = table.FullCopy(v) // recursion ho!
817 elseif (type(v) == "Vector") then
818 res[k] = Vector(v.x, v.y, v.z)
819 elseif (type(v) == "Angle") then
820 res[k] = Angle(v.p, v.y, v.r)
821 else
822 res[k] = v
823 end
824 end
825
826 return res
827
828 end
829
830end