local F=require(script.Parent)local c=require(script.Parent.LightningSparks)local t=Random.new()local D=os.clock function RandomVectorOffsetBetween(F,c,D)return((CFrame.lookAt(Vector3.new(),F)*CFrame.Angles(0,0,t:NextNumber(0,2*math.pi)))*CFrame.Angles(math.acos(t:NextNumber(math.cos(D),math.cos(c))),0,0)).LookVector end local C={}local U={}U.__index=U function U.new(m,O,S,B,N,f)local h=setmetatable({},U)h.Size=O or 1 h.NumBolts=S or 14 h.Color=B or ColorSequence.new(Color3.new(1,0,0),Color3.new(0,0,1))h.BoltColor=N or Color3.new(.3,.3,1)h.UpVector=f or Vector3.new(0,1,0)local j=workspace.CurrentCamera local p=Instance.new("\080\097\114\116")p.Name="\076\105\103\104\116\110\105\110\103\069\120\112\108\111\115\105\111\110"p.Anchored=true p.CanCollide=false p.Locked=true p.CastShadow=false p.Transparency=1 p.Size=Vector3.new(.05,.05,.05)p.CFrame=CFrame.lookAt(m+Vector3.new(0,.5,0),(m+Vector3.new(0,.5,0))+h.UpVector)*(CFrame.lookAt(Vector3.new(),Vector3.new(0,1,0))):inverse()p.Parent=j local b=Instance.new("\065\116\116\097\099\104\109\101\110\116")b.Parent=p b.CFrame=CFrame.new()local s=script.ExplosionBrightspot:Clone()local I=script.GlareEmitter:Clone()local L=script.PlasmaEmitter:Clone()local K=math.clamp(h.Size,0,1)I.Size=NumberSequence.new(30*K)L.Size=NumberSequence.new(18*K)L.Speed=NumberRange.new(100*K)s.Parent=b I.Parent=b L.Parent=b local A=h.Color if typeof(A)=="\067\111\108\111\114\051"then I.Color,L.Color=ColorSequence.new(A),ColorSequence.new(A)local F,c,t=Color3.toHSV(A)s.Color=ColorSequence.new(Color3.fromHSV(F,.5,t))else I.Color,L.Color=A,A local F=A.Keypoints for c=1,#F,1 do local t,D,C=Color3.toHSV(F[c].Value)F[c]=ColorSequenceKeypoint.new(F[c].Time,Color3.fromHSV(t,.5,C))end s.Color=ColorSequence.new(F)end s.Enabled,I.Enabled,L.Enabled=false,false,false local H={}for D=1,h.NumBolts,1 do local C,U={},{}C.WorldPosition,C.WorldAxis=b.WorldPosition,RandomVectorOffsetBetween(h.UpVector,math.rad(65),math.rad(80))U.WorldPosition,U.WorldAxis=b.WorldPosition+((C.WorldAxis*t:NextNumber(20,40))*1.4)*K,RandomVectorOffsetBetween(-h.UpVector,math.rad(70),math.rad(110))local m=F.new(C,U,10)m.AnimationSpeed=0 m.Thickness=1 m.Color=h.BoltColor m.PulseLength=.8 m.ColorOffsetSpeed=20 m.Frequency=2 m.MinRadius,m.MaxRadius=0,4*K m.FadeLength=.4 m.PulseSpeed=5 m.MinThicknessMultiplier,m.MaxThicknessMultiplier=.7,1 local O=c.new(m,5)O.MinDistance,O.MaxDistance=7.5,10 m.Velocity=((U.WorldPosition-C.WorldPosition).Unit*.1)*K H[#H+1]=m end h.Bolts=H h.Attachment=b h.Part=p h.StartT=D()h.RefIndex=#C+1 C[h.RefIndex]=h return h end function U.Destroy(F)C[F.RefIndex]=nil F.Part:Destroy()for c=1,#F.Bolts,1 do F.Bolts[c]=nil end F=nil end;(game:GetService("\082\117\110\083\101\114\118\105\099\101")).Heartbeat:Connect(function()for F,c in pairs(C)do local t=D()-c.StartT local C=c.Attachment if t<.7 then if t>.2 then C.ExplosionBrightspot.Enabled,C.GlareEmitter.Enabled,C.PlasmaEmitter.Enabled=false,false,false end for F=1,#c.Bolts,1 do local t=c.Bolts[F]t.Attachment1.WorldPosition=t.Attachment1.WorldPosition+t.Velocity end else c:Destroy()end end end)return U

local LightningBolt = require(script.Parent)
local LightningSparks = require(script.Parent.LightningSparks)

local rng_v = Random.new()
local clock = os.clock

function RandomVectorOffsetBetween(v, minAngle, maxAngle) --returns uniformly-distributed random unit vector no more than maxAngle radians away from v and no less than minAngle radians
    return (CFrame.lookAt(Vector3.new(), v)*CFrame.Angles(0, 0, rng_v:NextNumber(0, 2*math.pi))*CFrame.Angles(math.acos(rng_v:NextNumber(math.cos(maxAngle), math.cos(minAngle))), 0, 0)).LookVector
end


local ActiveExplosions = {}


local LightningExplosion = {}
LightningExplosion.__index = LightningExplosion

function LightningExplosion.new(Position, Size, NumBolts, Color, BoltColor, UpVector)
	local self = setmetatable({}, LightningExplosion)
	
	--Main (default) Properties--
	
		self.Size = Size or 1 --Value between 0 and 1 (1 for largest)
		self.NumBolts = NumBolts or 14 --Number of lightning bolts shot out from explosion
		self.Color = Color or ColorSequence.new(Color3.new(1, 0, 0), Color3.new(0, 0, 1)) --Can be a Color3 or ColorSequence
		self.BoltColor = BoltColor or Color3.new(0.3, 0.3, 1) --Can be a Color3 or ColorSequence
		self.UpVector = UpVector or Vector3.new(0, 1, 0) --Can be used to "rotate" the explosion
	
	--
	
	local parent = workspace.CurrentCamera
	
	local part = Instance.new("Part")
	part.Name = "LightningExplosion"
	part.Anchored = true
	part.CanCollide = false
	part.Locked = true
	part.CastShadow = false
	part.Transparency = 1
	part.Size = Vector3.new(0.05, 0.05, 0.05)
	part.CFrame = CFrame.lookAt(Position + Vector3.new(0, 0.5, 0), Position + Vector3.new(0, 0.5, 0) + self.UpVector)*CFrame.lookAt(Vector3.new(), Vector3.new(0, 1, 0)):inverse()
	part.Parent = parent
	
	local attach = Instance.new("Attachment")
	attach.Parent = part
	attach.CFrame = CFrame.new()
	
	local partEmit1 = script.ExplosionBrightspot:Clone()
	local partEmit2 = script.GlareEmitter:Clone()
	local partEmit3 = script.PlasmaEmitter:Clone()
	
	local size = math.clamp(self.Size, 0, 1)
	
	partEmit2.Size = NumberSequence.new(30*size)
	partEmit3.Size = NumberSequence.new(18*size)
	partEmit3.Speed = NumberRange.new(100*size)
	
	partEmit1.Parent = attach
	partEmit2.Parent = attach
	partEmit3.Parent = attach
	
	local color = self.Color
	
	if typeof(color) == "Color3" then
		partEmit2.Color, partEmit3.Color = ColorSequence.new(color), ColorSequence.new(color)
		local cH, cS, cV = Color3.toHSV(color)
		partEmit1.Color = ColorSequence.new(Color3.fromHSV(cH, 0.5, cV))
	else --ColorSequence
		partEmit2.Color, partEmit3.Color = color, color
		local keypoints = color.Keypoints 
		for i = 1, #keypoints do
			local cH, cS, cV = Color3.toHSV(keypoints[i].Value)
			keypoints[i] = ColorSequenceKeypoint.new(keypoints[i].Time, Color3.fromHSV(cH, 0.5, cV))
		end
		partEmit1.Color = ColorSequence.new(keypoints)
	end
	
	partEmit1.Enabled, partEmit2.Enabled, partEmit3.Enabled = false,false,false
	
	local bolts = {}
	
	for i = 1, self.NumBolts do
		local A1, A2 = {}, {}

		A1.WorldPosition, A1.WorldAxis = attach.WorldPosition, RandomVectorOffsetBetween(self.UpVector, math.rad(65), math.rad(80))
		A2.WorldPosition, A2.WorldAxis = attach.WorldPosition + A1.WorldAxis*rng_v:NextNumber(20, 40)*1.4*size, RandomVectorOffsetBetween(-self.UpVector, math.rad(70), math.rad(110))
		--local curve0, curve1 = rng_v:NextNumber(0, 10)*size, rng_v:NextNumber(0, 10)*size
		local NewBolt = LightningBolt.new(A1, A2, 10)
		NewBolt.AnimationSpeed = 0
		NewBolt.Thickness = 1 --*size
		NewBolt.Color = self.BoltColor
		NewBolt.PulseLength = 0.8
		NewBolt.ColorOffsetSpeed = 20
		NewBolt.Frequency = 2
		NewBolt.MinRadius, NewBolt.MaxRadius = 0, 4*size
		NewBolt.FadeLength = 0.4
		NewBolt.PulseSpeed = 5
		NewBolt.MinThicknessMultiplier, NewBolt.MaxThicknessMultiplier = 0.7, 1

		local NewSparks = LightningSparks.new(NewBolt, 5)
		NewSparks.MinDistance, NewSparks.MaxDistance = 7.5, 10
		
		NewBolt.Velocity = (A2.WorldPosition - A1.WorldPosition).Unit*0.1*size
		--NewBolt.v0, NewBolt.v1 = rng_v:NextNumber(0, 5)*size, rng_v:NextNumber(0, 5)*size
		
		bolts[#bolts + 1] = NewBolt
	end
	
	self.Bolts = bolts
	self.Attachment = attach
	self.Part = part
	self.StartT = clock()
	self.RefIndex = #ActiveExplosions + 1

	ActiveExplosions[self.RefIndex] = self

	return self
end

function LightningExplosion:Destroy()
	ActiveExplosions[self.RefIndex] = nil
	self.Part:Destroy()
	
	for i = 1, #self.Bolts do
		self.Bolts[i] = nil
	end
	
	self = nil
end

game:GetService("RunService").Heartbeat:Connect(function ()
	
	for _, ThisExplosion in pairs(ActiveExplosions) do
		
		local timePassed = clock() - ThisExplosion.StartT
		local attach = ThisExplosion.Attachment
		
		if timePassed < 0.7 then 
			
			if timePassed > 0.2 then
				attach.ExplosionBrightspot.Enabled, attach.GlareEmitter.Enabled, attach.PlasmaEmitter.Enabled = false, false, false
			end
			
			for i = 1, #ThisExplosion.Bolts do 
				
				local currBolt = ThisExplosion.Bolts[i]
				currBolt.Attachment1.WorldPosition = currBolt.Attachment1.WorldPosition + currBolt.Velocity
				--currBolt.CurveSize0, currBolt.CurveSize1 = currBolt.CurveSize0 + currBolt.v0, currBolt.CurveSize1 + currBolt.v1
				
			end
			
		else
			
			ThisExplosion:Destroy()
			
		end
		
	end
	
end)




return LightningExplosion
