· 8 years ago · Jun 10, 2018, 03:52 PM
1/*============================================================================================
2
3 DubstepGun Addon-recoded: Created By Auzlex
4
5 Under the copyright (C) protection of DMCA.
6
7 My Terms are simply are:
8
9 You can edit and learn the code freely however you shall not claim or be proud for any
10 additional modificaitons to the current script, doing so i will have to take serious action of
11 punching your face in or simply hunting you and your scripted modified version of this mod like a raccoon in the woods.
12
13 Anyways you will not learn anything from just looking and copying bits of code, I suggest you
14 attemp to make a addon/mod that is 100% made by you and that you can be proud of it without the
15 shame of using someone else code, in other words learn by building up your skill.
16
17 You shall not:
18
19 - Re-upload to another site or workshop even spamming the description of who oringally made it and a link to the orignal addon.
20 - Claim that you made any bit of this script.
21
22 Final and last statement JUST DONT STEAL ANYTHING, and thank you for your great time for reading all
23 of this.
24
25============================================================================================*/
26
27if SERVER then
28 AddCSLuaFile("shared.lua");
29end
30
31SWEP.Weight = 10
32SWEP.AutoSwitchTo = false
33SWEP.AutoSwitchFrom = false
34SWEP.FiresUnderwater = false
35SWEP.Base = "weapon_base"
36SWEP.BounceWeaponIcon = false
37SWEP.Spawnable = false
38
39SWEP.SkinType = 0
40SWEP.MusicString = "sound/weapons/dubstepgun/songs/classical.mp3"
41SWEP.MusicDullString = "weapons/dubstepgun/songs/dullsounds/classicaln_loop.wav"
42SWEP.MaterialString = ""
43SWEP.WeaponID = nil
44SWEP.IsPlayingSong = false
45
46if ( CLIENT ) then
47
48 SWEP.PrintName = "Dubstepgun base"
49 SWEP.Author = "Auzlex"
50 SWEP.Instructions = "Wait what? how did you get this this is not to be found!"
51 SWEP.Contact = "bluevortexdev@gmail.com"
52 SWEP.Purpose = "Wait what? how did you get this this is not to be found!"
53
54 SWEP.Category = "Dubstep Guns -- SR4"
55 SWEP.Slot = 4
56 SWEP.SlotPos = 4
57 SWEP.DrawAmmo = false
58 SWEP.DrawCrosshair = true
59 SWEP.Icon = "noicon"
60
61end
62
63local BarColor = {
64 [0] = Color(190, 0, 0), -- Over 0% -> Red
65 [5] = Color(255, 255, 0), -- Over 25 % -> Yellow
66 [10] = Color(0, 255, 0), -- Over 50% -> Green
67 [15] = Color(100, 255, 100) -- Over 50% -> Green
68}
69
70function GetBarColor(p)
71 local barcolor = Color(0,0,0)
72
73 for i,v in pairs(BarColor) do
74 if p > i then
75 barcolor = v
76 end
77 end
78
79 return barcolor
80end
81
82SWEP.WElements = {
83 ["dubstepgun"] = { type = "Model", model = "models/mark2580/sr4/dubstepgun.mdl", bone = "ValveBiped.Bip01_R_Hand", rel = "", pos = Vector(0.842, -3.415, 1.97), angle = Angle(-164.805, 176.494, 0), size = Vector(1, 1, 1), color = Color(255, 255, 255, 255), surpresslightning = false, material = "", skin = SWEP.SkinType, bodygroup = {} }
84}
85SWEP.VElements = {
86 ["firstperson_dubstepgun"] = { type = "Model", model = "models/mark2580/sr4/dubstepgun.mdl", bone = "base", rel = "", pos = Vector(-4.561, 7.835, -2.845), angle = Angle(90, -90, 0), size = Vector(1, 1, 1), color = Color(255, 255, 255, 255), surpresslightning = false, material = "", skin = SWEP.SkinType, bodygroup = {} },
87 ["hud"] = { type = "Quad", bone = "base", rel = "firstperson_dubstepgun", pos = Vector(18.766, -5.689, 10.895), angle = Angle(86.945, 6.793, 1.986), size = 0.174,
88 draw_func = function()
89
90 local w, h = 25, 50
91
92 --draw.RoundedBox( 0, -13, -27, w, h, Color( 40, 40, 40, 30 ) )
93
94 local bars = 25
95 local ffttable = {}
96 local FFTTableSmooth = {}
97
98 if IsValid( ClientStation ) then
99
100 ClientStation:FFT( ffttable, bars )
101
102 for k=1, bars do
103
104 FFTTableSmooth[k] = 0
105
106 end
107
108 for k=1, bars do
109
110 if ffttable[k] == nil then ffttable[k] = 0 end
111
112 FFTTableSmooth[k] = Lerp( 20 * FrameTime(), FFTTableSmooth[k], ffttable[k] * 100 )
113
114 local barcolor = GetBarColor(k * 1)
115 draw.RoundedBox( 0, (( k * 2.5 )/2)-14, 20, 1, -FFTTableSmooth[k], barcolor )
116
117 end
118
119 end
120
121 end
122 }
123}
124
125
126SWEP.AdminOnly = false
127SWEP.UseHands = true
128SWEP.ViewModel = "models/weapons/c_rpg.mdl"
129SWEP.WorldModel = "models/weapons/w_rocket_launcher.mdl"
130SWEP.ShowWorldModel = false
131SWEP.ShowViewModel = true
132SWEP.HoldType = "rpg"
133
134SWEP.PreventEffectSpam = false
135SWEP.PreventEffectSpam2 = false
136SWEP.AllowBounce = false
137
138SWEP.ViewModelBoneMods = {
139 ["ValveBiped.Bip01_R_Hand"] = { scale = Vector(1, 1, 1), pos = Vector(-22, -10, -4), angle = Angle( 90, 0, 40) }
140}
141
142SWEP.Primary.Damage = 0
143SWEP.Primary.TakeAmmo = 0
144SWEP.Primary.ClipSize = -1
145SWEP.Primary.Ammo = "none"
146SWEP.Primary.DefaultClip = 0
147
148SWEP.Secondary.Damage = 0
149SWEP.Secondary.TakeAmmo = 0
150SWEP.Secondary.ClipSize = -1
151SWEP.Secondary.Ammo = "none"
152SWEP.Secondary.DefaultClip = 0
153
154SWEP.DisableDullMusic = false
155
156--[[
157
158 Swep Functions
159
160]]--
161
162function SWEP:BeginWeaponSetUp()
163
164 if !IsValid( self.Owner ) then return end
165
166 if CLIENT then
167
168 self.WeaponID = tostring( self.Owner:Nick() )
169
170 end
171
172 if SERVER then
173
174 self.WeaponID = tostring( self.Owner:Nick() )
175
176 self.Owner:SetNWString( "dubstepgun.id", tostring( self.Owner:Nick() ) )
177 self.Owner:SetNWString( "dubstepgun.song", self.MusicString )
178
179 util.AddNetworkString( "dubstepgun.network.fire.id=" .. self.WeaponID )
180 util.AddNetworkString( "dubstepgun.network.fire.treb.id=" .. self.WeaponID )
181
182 net.Receive( "dubstepgun.network.fire.id=" .. tostring( self.Owner:GetName() ), function( Length, Ply )
183
184 if !IsValid( self.Owner ) or !IsValid( self.Weapon ) then return end
185 if self.PreventEffectSpam == true then return end
186
187 self.PreventEffectSpam = true
188 self.AllowBounce = true
189
190 timer.Simple( 0.3, function() self.PreventEffectSpam = false end )
191 timer.Simple( 0.45, function() self.AllowBounce = false end )
192
193 if IsValid( Ply ) then
194
195 local tr = self.Owner:GetEyeTrace()
196
197 local effectdata = EffectData()
198 effectdata:SetOrigin( tr.HitPos )
199 util.Effect( "dubstep_wub_effect", effectdata, true, true )
200
201 local effectdata = EffectData()
202 effectdata:SetOrigin( tr.HitPos )
203 effectdata:SetStart( self.Owner:GetShootPos() )
204 effectdata:SetScale( 5 )
205 effectdata:SetAttachment( 1 )
206 effectdata:SetEntity( self.Weapon )
207 util.Effect( "dubstep_wub_beam", effectdata, true, true )
208
209 util.BlastDamage( self.Weapon, self.Owner, tr.HitPos, 70, 140 )
210
211 end
212
213 end )
214
215 net.Receive( "dubstepgun.network.fire.treb.id=" .. tostring( self.Owner:GetName() ), function( Length, Ply )
216
217 if !IsValid( self.Owner ) or !IsValid( self.Weapon ) then return end
218 if self.PreventEffectSpam2 == true then return end
219
220 self.PreventEffectSpam2 = true
221 --self.AllowBounce = true
222
223 timer.Simple( 0.3, function() self.PreventEffectSpam2 = false end )
224 --timer.Simple( 0.45, function() self.AllowBounce = false end )
225
226 if IsValid( Ply ) then
227
228 local tr = self.Owner:GetEyeTrace()
229
230
231 --local righthand = self.Owner:LookupAttachment("0")
232 local posang = self.Owner:GetAttachment(1)
233
234 local effectdata = EffectData()
235 effectdata:SetOrigin( posang.Pos + posang.Ang:Right()*2 )--posang.Pos + posang.Ang:Forward()*10 + posang.Ang:Up()*9.5 + posang.Ang:Right() * 5 )
236 effectdata:SetEntity( self.Weapon )
237 effectdata:SetNormal( tr.HitNormal )
238 util.Effect( "dubstep_wub_treb_effect", effectdata, true, true )
239
240
241 --[[local effectdata = EffectData()
242 effectdata:SetOrigin( tr.HitPos )
243 effectdata:SetStart( self.Owner:GetShootPos() )
244 effectdata:SetScale( 5 )
245 effectdata:SetAttachment( 1 )
246 effectdata:SetEntity( self.Weapon )
247 util.Effect( "dubstep_wub_beam", effectdata, true, true )]]
248
249 --util.BlastDamage( self.Weapon, self.Owner, tr.HitPos, 250, 150 )
250
251 end
252
253 end )
254
255 end
256
257end
258
259function SWEP:Initialize()
260
261 self:SetWeaponHoldType( self.HoldType )
262
263 if SERVER then
264
265 --self:BeginWeaponSetUp()
266
267 end
268
269 if CLIENT then
270
271 -- Create a new table for every weapon instance
272 self.VElements = table.FullCopy( self.VElements )
273 self.WElements = table.FullCopy( self.WElements )
274 self.ViewModelBoneMods = table.FullCopy( self.ViewModelBoneMods )
275
276 self:CreateModels(self.VElements) -- create viewmodels
277 self:CreateModels(self.WElements) -- create worldmodels
278
279 -- init view model bone build function
280 if IsValid(self.Owner) then
281 local vm = self.Owner:GetViewModel()
282 if IsValid(vm) then
283 self:ResetBonePositions(vm)
284
285 -- Init viewmodel visibility
286 if (self.ShowViewModel == nil or self.ShowViewModel) then
287 vm:SetColor(Color(255,255,255,255))
288 else
289 -- we set the alpha to 1 instead of 0 because else ViewModelDrawn stops being called
290 vm:SetColor(Color(255,255,255,1))
291 -- ^ stopped working in GMod 13 because you have to do Entity:SetRenderMode(1) for translucency to kick in
292 -- however for some reason the view model resets to render mode 0 every frame so we just apply a debug material to prevent it from drawing
293 vm:SetMaterial("Debug/hsv")
294 end
295 end
296 end
297
298 end
299
300 return true
301end
302
303--[[
304
305 Music SWEP functions
306
307]]--
308
309function SWEP:BeginMusic()
310
311 if self.WeaponID == nil then return false end
312
313 if not self.IsPlayingSong then
314
315 if SERVER then
316
317 umsg.Start( self.WeaponID, self.Owner )
318 umsg.Bool( true ) -- true to play the set song, false to stop music
319 umsg.String( self.MusicString )
320 umsg.Entity( self.Owner )
321 umsg.Bool( false )
322 umsg.End()
323
324 end
325
326 self.IsPlayingSong = true
327
328 end
329
330end
331
332
333function SWEP:EndMusic()
334
335 if self.WeaponID == nil then return false end
336
337 if self.IsPlayingSong then
338
339 if SERVER then
340
341 umsg.Start( self.WeaponID, self.Owner )
342 umsg.Bool( false ) -- true to play the set song, false to stop music
343 umsg.String( self.MusicString )
344 umsg.Entity( self.Owner )
345 umsg.Bool( false )
346 umsg.End()
347 if CLIENT then
348 self.Owner:EmitSound( "weapons/dubstepgun/dubstep_shutdown2.wav", 100, 100 )
349 end
350 self.AllowBounce = false
351
352 end
353
354 self.IsPlayingSong = false
355
356 end
357
358end
359
360--[[
361
362 The Dull music playing while holding swep functions
363
364]]--
365
366function SWEP:BeginDullMusic()
367
368 if(self.DisableDullMusic == true) then return end;
369
370 if !self.DullMusicSound then
371
372 self.DullMusicSound = CreateSound( self.Owner, Sound( self.MusicDullString ) )
373 self.DullMusicSound:Play()
374
375 end
376
377end
378
379function SWEP:EndDullMusic()
380
381 if(self.DisableDullMusic == true) then return end;
382
383 if self.DullMusicSound then
384
385 if self.DullMusicSound:IsPlaying() then
386
387 self.DullMusicSound:Stop()
388 self.DullMusicSound = nil
389
390 end
391
392 end
393
394end
395
396--[[
397
398 More Swep Functions
399
400]]--
401
402function SWEP:PrimaryAttack()
403
404 self:BeginMusic()
405 self:EndDullMusic()
406
407
408 self.Weapon:SetNextPrimaryFire(CurTime()+1);
409 self.Weapon:SetNextSecondaryFire(CurTime()+1);
410
411 return true
412end
413
414
415function SWEP:SecondaryAttack()
416
417 self:EndMusic()
418 self:BeginDullMusic()
419
420 self.Weapon:SetNextSecondaryFire(CurTime()+1);
421 self.Weapon:SetNextPrimaryFire(CurTime()+1);
422
423 return true
424end
425
426function SWEP:Reload()
427 return false
428end
429
430function SWEP:Deploy()
431
432 self:BeginWeaponSetUp()
433
434 if IsValid( self.Weapon ) and IsValid( self.Owner ) and self.Owner:Alive() then
435
436 self.Weapon:SendWeaponAnim(ACT_VM_DRAW);
437
438 if SERVER then
439
440 self:BeginDullMusic()
441
442 end
443
444 end
445
446 return true
447end
448
449function SWEP:Holster()
450
451 if IsValid( self.Owner ) and self.Owner:Alive() then
452
453 self:EndMusic()
454
455 if SERVER then
456
457 self:EndDullMusic()
458
459 end
460
461 end
462
463 if CLIENT and IsValid(self.Owner) then
464 local vm = self.Owner:GetViewModel()
465 if IsValid(vm) then
466 self:ResetBonePositions(vm)
467 end
468 end
469
470 return true
471end
472
473function SWEP:OnDrop()
474 self:Holster()
475end
476
477function SWEP:OnRemove()
478 self:Holster()
479end
480
481function SWEP:Think()
482
483 if CLIENT then return end
484
485 if !IsValid( self.Owner ) or !IsValid( self.Weapon ) then return end
486
487 if IsValid( self.Owner ) then
488
489 for k, v in ipairs( ents.GetAll() ) do
490
491 if IsValid( v ) then
492
493 if string.match( string.lower( v:GetClass() ), "prop_physics" ) and self.AllowBounce == true then
494
495 if v:GetPos():Distance( self.Owner:GetPos() ) < 20 then
496
497 local v_physics = v:GetPhysicsObject()
498
499 if IsValid( v_physics ) then
500
501 v:Activate()
502 v:SetMoveType( MOVETYPE_VPHYSICS )
503 v_physics:Wake()
504 v_physics:ApplyForceCenter( Vector( 0, 0, 30 ) * v_physics:GetMass() )
505
506 end
507
508 end
509
510 elseif string.match( string.lower( v:GetClass() ), "prop_vehicle" ) and self.AllowBounce == true then
511
512 if v:GetPos():Distance( self.Owner:GetPos() ) < 3000 then
513
514 local v_physics = v:GetPhysicsObject()
515
516 if IsValid( v_physics ) then
517
518 v:Activate()
519 v:SetMoveType( MOVETYPE_VPHYSICS )
520 v_physics:Wake()
521 v_physics:ApplyForceCenter( Vector( 0, 0, 100 ) * v_physics:GetMass() )
522
523 end
524
525 end
526
527 end
528
529 end
530
531 end
532
533 end
534
535end
536
537if CLIENT then
538
539 SWEP.vRenderOrder = nil
540 function SWEP:ViewModelDrawn()
541
542 local vm = self.Owner:GetViewModel()
543 if !IsValid(vm) then return end
544
545
546
547 if (!self.VElements) then return end
548
549 self:UpdateBonePositions(vm)
550
551 if (!self.vRenderOrder) then
552
553 -- we build a render order because sprites need to be drawn after models
554 self.vRenderOrder = {}
555
556 for k, v in pairs( self.VElements ) do
557 if (v.type == "Model") then
558 table.insert(self.vRenderOrder, 1, k)
559 elseif (v.type == "Sprite" or v.type == "Quad") then
560 table.insert(self.vRenderOrder, k)
561 end
562 end
563
564 end
565
566 for k, name in ipairs( self.vRenderOrder ) do
567
568 local v = self.VElements[name]
569 if (!v) then self.vRenderOrder = nil break end
570 if (v.hide) then continue end
571
572 local model = v.modelEnt
573 local sprite = v.spriteMaterial
574
575 if (!v.bone) then continue end
576
577 local pos, ang = self:GetBoneOrientation( self.VElements, v, vm )
578
579 if (!pos) then continue end
580
581 if (v.type == "Model" and IsValid(model)) then
582
583 model:SetPos(pos + ang:Forward() * v.pos.x + ang:Right() * v.pos.y + ang:Up() * v.pos.z )
584 ang:RotateAroundAxis(ang:Up(), v.angle.y)
585 ang:RotateAroundAxis(ang:Right(), v.angle.p)
586 ang:RotateAroundAxis(ang:Forward(), v.angle.r)
587
588 model:SetAngles(ang)
589 --model:SetModelScale(v.size)
590 local matrix = Matrix()
591 matrix:Scale(v.size)
592 model:EnableMatrix( "RenderMultiply", matrix )
593
594 if (v.material == "") then
595 model:SetMaterial("")
596 elseif (model:GetMaterial() != v.material) then
597 model:SetMaterial( v.material )
598 end
599
600 if (v.skin and v.skin != model:GetSkin()) then
601 model:SetSkin(v.skin)
602 end
603
604 if (v.bodygroup) then
605 for k, v in pairs( v.bodygroup ) do
606 if (model:GetBodygroup(k) != v) then
607 model:SetBodygroup(k, v)
608 end
609 end
610 end
611
612 if (v.surpresslightning) then
613 render.SuppressEngineLighting(true)
614 end
615
616 render.SetColorModulation(v.color.r/255, v.color.g/255, v.color.b/255)
617 render.SetBlend(v.color.a/255)
618 model:DrawModel()
619 render.SetBlend(1)
620 render.SetColorModulation(1, 1, 1)
621
622 if (v.surpresslightning) then
623 render.SuppressEngineLighting(false)
624 end
625
626 elseif (v.type == "Sprite" and sprite) then
627
628 local drawpos = pos + ang:Forward() * v.pos.x + ang:Right() * v.pos.y + ang:Up() * v.pos.z
629 render.SetMaterial(sprite)
630 render.DrawSprite(drawpos, v.size.x, v.size.y, v.color)
631
632 elseif (v.type == "Quad" and v.draw_func) then
633
634 local drawpos = pos + ang:Forward() * v.pos.x + ang:Right() * v.pos.y + ang:Up() * v.pos.z
635 ang:RotateAroundAxis(ang:Up(), v.angle.y)
636 ang:RotateAroundAxis(ang:Right(), v.angle.p)
637 ang:RotateAroundAxis(ang:Forward(), v.angle.r)
638
639 cam.Start3D2D(drawpos, ang, v.size)
640 v.draw_func( self )
641 cam.End3D2D()
642
643 end
644
645 end
646
647 end
648
649 SWEP.wRenderOrder = nil
650 function SWEP:DrawWorldModel()
651
652 if (self.ShowWorldModel == nil or self.ShowWorldModel) then
653 self:DrawModel()
654 end
655
656 if (!self.WElements) then return end
657
658 if (!self.wRenderOrder) then
659
660 self.wRenderOrder = {}
661
662 for k, v in pairs( self.WElements ) do
663 if (v.type == "Model") then
664 table.insert(self.wRenderOrder, 1, k)
665 elseif (v.type == "Sprite" or v.type == "Quad") then
666 table.insert(self.wRenderOrder, k)
667 end
668 end
669
670 end
671
672 if (IsValid(self.Owner)) then
673 bone_ent = self.Owner
674 else
675 -- when the weapon is dropped
676 bone_ent = self
677 end
678
679 for k, name in pairs( self.wRenderOrder ) do
680
681 local v = self.WElements[name]
682 if (!v) then self.wRenderOrder = nil break end
683 if (v.hide) then continue end
684
685 local pos, ang
686
687 if (v.bone) then
688 pos, ang = self:GetBoneOrientation( self.WElements, v, bone_ent )
689 else
690 pos, ang = self:GetBoneOrientation( self.WElements, v, bone_ent, "ValveBiped.Bip01_R_Hand" )
691 end
692
693 if (!pos) then continue end
694
695 local model = v.modelEnt
696 local sprite = v.spriteMaterial
697
698 if (v.type == "Model" and IsValid(model)) then
699
700 model:SetPos(pos + ang:Forward() * v.pos.x + ang:Right() * v.pos.y + ang:Up() * v.pos.z )
701 ang:RotateAroundAxis(ang:Up(), v.angle.y)
702 ang:RotateAroundAxis(ang:Right(), v.angle.p)
703 ang:RotateAroundAxis(ang:Forward(), v.angle.r)
704
705 model:SetAngles(ang)
706 --model:SetModelScale(v.size)
707 local matrix = Matrix()
708 matrix:Scale(v.size)
709 model:EnableMatrix( "RenderMultiply", matrix )
710
711 if (v.material == "") then
712 model:SetMaterial("")
713 elseif (model:GetMaterial() != v.material) then
714 model:SetMaterial( v.material )
715 end
716
717 if (v.skin and v.skin != model:GetSkin()) then
718 model:SetSkin(v.skin)
719 end
720
721 if (v.bodygroup) then
722 for k, v in pairs( v.bodygroup ) do
723 if (model:GetBodygroup(k) != v) then
724 model:SetBodygroup(k, v)
725 end
726 end
727 end
728
729 if (v.surpresslightning) then
730 render.SuppressEngineLighting(true)
731 end
732
733 render.SetColorModulation(v.color.r/255, v.color.g/255, v.color.b/255)
734 render.SetBlend(v.color.a/255)
735 model:DrawModel()
736 render.SetBlend(1)
737 render.SetColorModulation(1, 1, 1)
738
739 if (v.surpresslightning) then
740 render.SuppressEngineLighting(false)
741 end
742
743 elseif (v.type == "Sprite" and sprite) then
744
745 local drawpos = pos + ang:Forward() * v.pos.x + ang:Right() * v.pos.y + ang:Up() * v.pos.z
746 render.SetMaterial(sprite)
747 render.DrawSprite(drawpos, v.size.x, v.size.y, v.color)
748
749 elseif (v.type == "Quad" and v.draw_func) then
750
751 local drawpos = pos + ang:Forward() * v.pos.x + ang:Right() * v.pos.y + ang:Up() * v.pos.z
752 ang:RotateAroundAxis(ang:Up(), v.angle.y)
753 ang:RotateAroundAxis(ang:Right(), v.angle.p)
754 ang:RotateAroundAxis(ang:Forward(), v.angle.r)
755
756 cam.Start3D2D(drawpos, ang, v.size)
757 v.draw_func( self )
758 cam.End3D2D()
759
760 end
761
762 end
763
764 end
765
766 function SWEP:GetBoneOrientation( basetab, tab, ent, bone_override )
767
768 local bone, pos, ang
769 if (tab.rel and tab.rel != "") then
770
771 local v = basetab[tab.rel]
772
773 if (!v) then return end
774
775 -- Technically, if there exists an element with the same name as a bone
776 -- you can get in an infinite loop. Let's just hope nobody's that stupid.
777 pos, ang = self:GetBoneOrientation( basetab, v, ent )
778
779 if (!pos) then return end
780
781 pos = pos + ang:Forward() * v.pos.x + ang:Right() * v.pos.y + ang:Up() * v.pos.z
782 ang:RotateAroundAxis(ang:Up(), v.angle.y)
783 ang:RotateAroundAxis(ang:Right(), v.angle.p)
784 ang:RotateAroundAxis(ang:Forward(), v.angle.r)
785
786 else
787
788 bone = ent:LookupBone(bone_override or tab.bone)
789
790 if (!bone) then return end
791
792 pos, ang = Vector(0,0,0), Angle(0,0,0)
793 local m = ent:GetBoneMatrix(bone)
794 if (m) then
795 pos, ang = m:GetTranslation(), m:GetAngles()
796 end
797
798 if (IsValid(self.Owner) and self.Owner:IsPlayer() and
799 ent == self.Owner:GetViewModel() and self.ViewModelFlip) then
800 ang.r = -ang.r -- Fixes mirrored models
801 end
802
803 end
804
805 return pos, ang
806 end
807
808 function SWEP:CreateModels( tab )
809
810 if (!tab) then return end
811
812 -- Create the clientside models here because Garry says we can't do it in the render hook
813 for k, v in pairs( tab ) do
814 if (v.type == "Model" and v.model and v.model != "" and (!IsValid(v.modelEnt) or v.createdModel != v.model) and
815 string.find(v.model, ".mdl") and file.Exists (v.model, "GAME") ) then
816
817 v.modelEnt = ClientsideModel(v.model, RENDER_GROUP_VIEW_MODEL_OPAQUE)
818 if (IsValid(v.modelEnt)) then
819 v.modelEnt:SetPos(self:GetPos())
820 v.modelEnt:SetAngles(self:GetAngles())
821 v.modelEnt:SetParent(self)
822 v.modelEnt:SetNoDraw(true)
823 v.createdModel = v.model
824 else
825 v.modelEnt = nil
826 end
827
828 elseif (v.type == "Sprite" and v.sprite and v.sprite != "" and (!v.spriteMaterial or v.createdSprite != v.sprite)
829 and file.Exists ("materials/"..v.sprite..".vmt", "GAME")) then
830
831 local name = v.sprite.."-"
832 local params = { ["$basetexture"] = v.sprite }
833 -- make sure we create a unique name based on the selected options
834 local tocheck = { "nocull", "additive", "vertexalpha", "vertexcolor", "ignorez" }
835 for i, j in pairs( tocheck ) do
836 if (v[j]) then
837 params["$"..j] = 1
838 name = name.."1"
839 else
840 name = name.."0"
841 end
842 end
843
844 v.createdSprite = v.sprite
845 v.spriteMaterial = CreateMaterial(name,"UnlitGeneric",params)
846
847 end
848 end
849
850 end
851
852 local allbones
853 local hasGarryFixedBoneScalingYet = false
854
855 function SWEP:UpdateBonePositions(vm)
856
857 if self.ViewModelBoneMods then
858
859 if (!vm:GetBoneCount()) then return end
860
861 -- !! WORKAROUND !! --
862 -- We need to check all model names :/
863 local loopthrough = self.ViewModelBoneMods
864 if (!hasGarryFixedBoneScalingYet) then
865 allbones = {}
866 for i=0, vm:GetBoneCount() do
867 local bonename = vm:GetBoneName(i)
868 if (self.ViewModelBoneMods[bonename]) then
869 allbones[bonename] = self.ViewModelBoneMods[bonename]
870 else
871 allbones[bonename] = {
872 scale = Vector(1,1,1),
873 pos = Vector(0,0,0),
874 angle = Angle(0,0,0)
875 }
876 end
877 end
878
879 loopthrough = allbones
880 end
881 -- !! ----------- !! --
882
883 for k, v in pairs( loopthrough ) do
884 local bone = vm:LookupBone(k)
885 if (!bone) then continue end
886
887 -- !! WORKAROUND !! --
888 local s = Vector(v.scale.x,v.scale.y,v.scale.z)
889 local p = Vector(v.pos.x,v.pos.y,v.pos.z)
890 local ms = Vector(1,1,1)
891 if (!hasGarryFixedBoneScalingYet) then
892 local cur = vm:GetBoneParent(bone)
893 while(cur >= 0) do
894 local pscale = loopthrough[vm:GetBoneName(cur)].scale
895 ms = ms * pscale
896 cur = vm:GetBoneParent(cur)
897 end
898 end
899
900 s = s * ms
901 -- !! ----------- !! --
902
903 if vm:GetManipulateBoneScale(bone) != s then
904 vm:ManipulateBoneScale( bone, s )
905 end
906 if vm:GetManipulateBoneAngles(bone) != v.angle then
907 vm:ManipulateBoneAngles( bone, v.angle )
908 end
909 if vm:GetManipulateBonePosition(bone) != p then
910 vm:ManipulateBonePosition( bone, p )
911 end
912 end
913 else
914 self:ResetBonePositions(vm)
915 end
916
917 end
918
919 function SWEP:ResetBonePositions(vm)
920
921 if (!vm:GetBoneCount()) then return end
922 for i=0, vm:GetBoneCount() do
923 vm:ManipulateBoneScale( i, Vector(1, 1, 1) )
924 vm:ManipulateBoneAngles( i, Angle(0, 0, 0) )
925 vm:ManipulateBonePosition( i, Vector(0, 0, 0) )
926 end
927
928 end
929
930 /**************************
931 Global utility code
932 **************************/
933
934 -- Fully copies the table, meaning all tables inside this table are copied too and so on (normal table.Copy copies only their reference).
935 -- Does not copy entities of course, only copies their reference.
936 -- WARNING: do not use on tables that contain themselves somewhere down the line or you'll get an infinite loop
937 function table.FullCopy( tab )
938
939 if (!tab) then return nil end
940
941 local res = {}
942 for k, v in pairs( tab ) do
943 if (type(v) == "table") then
944 res[k] = table.FullCopy(v) -- recursion ho!
945 elseif (type(v) == "Vector") then
946 res[k] = Vector(v.x, v.y, v.z)
947 elseif (type(v) == "Angle") then
948 res[k] = Angle(v.p, v.y, v.r)
949 else
950 res[k] = v
951 end
952 end
953
954 return res
955
956 end
957
958end