local function e()if Player.Character.Humanoid:GetState()==Enum.HumanoidStateType.Swimming then return end if CanFire then CanFire=false local e=table.remove(Buffer,1)e.Rocket.Transparency=0 Tool.FireRocket:FireServer(e)local l=(Mouse.Hit.p-Handle.Position).unit local Z=l*5 e.PrimaryPart.CFrame=CFrame.new(Handle.Position,Handle.Position+Z)+Z e.PrimaryPart.Velocity=Z*40 RocketManager:BindRocketEvents(e)wait(Configurations.ReloadTimeSeconds.Value)CanFire=true end end local function l(e)table.insert(Buffer,e)end local function Z()local e=Player.Character.Torso Neck=e.Neck OldNeckC0=Neck.C0 Shoulder=e["\082\105\103\104\116 \083\104\111\117\108\100\101\114"]OldShoulderC0=Shoulder.C0 end local function j(e)if Player.Character.Humanoid:GetState()==Enum.HumanoidStateType.Swimming then return end local l=Player.Character.HumanoidRootPart local Z=Player.Character.Head local j=(e-Z.Position).unit local v=math.acos(j:Dot(Vector3.new(0,1,0)))local D=v if math.deg(D)>110 then D=math.rad(110)end Neck.C0=CFrame.new(0,1,0)*CFrame.Angles(math.pi-D,math.pi,0)local q=Player.Character["\082\105\103\104\116 \065\114\109"]local h=l.Position+l.CFrame:vectorToWorldSpace(Vector3.new(l.Size.X/2+q.Size.X/2,l.Size.Y/2-q.Size.Z/2,0))local c=((e-h)*Vector3.new(1,0,1)).unit local Y=(l.CFrame.lookVector*Vector3.new(1,0,1)).unit local X=math.acos(c:Dot(Y))if tostring(X)=="-\049\046\035\073\078\068"then X=0 end if Player.Character.Humanoid:GetState()==Enum.HumanoidStateType.Seated then local e=l.CFrame.lookVector:Cross(c)if X>math.pi/2 then X=math.pi/2 end if e.Y<0 then X=-X end end Shoulder.C0=CFrame.new(1,.5,0)*CFrame.Angles(math.pi/2-v,math.pi/2+X,0)if Player.Character.Humanoid:GetState()~=Enum.HumanoidStateType.Seated then l.CFrame=CFrame.new(l.Position,l.Position+(Vector3.new(e.X,l.Position.Y,e.Z)-l.Position).unit)end end local function v()j(Mouse.Hit.p)end local function D()Z()OldMouseIcon=Mouse.Icon Mouse.Icon="\114\098\120\097\115\115\101\116\105\100\058\047\047\055\057\054\053\056\052\052\057"Mouse.TargetFilter=Player.Character AutoRotate=Player.Character.Humanoid.AutoRotate Player.Character.Humanoid.AutoRotate=false RunService:BindToRenderStep("\082\111\116\097\116\101\067\104\097\114\097\099\116\101\114",Enum.RenderPriority.Input.Value,v)end local function q()Mouse.Icon=OldMouseIcon Neck.C0=OldNeckC0 Shoulder.C0=OldShoulderC0 Player.Character.Humanoid.AutoRotate=AutoRotate RunService:UnbindFromRenderStep("\082\111\116\097\116\101\067\104\097\114\097\099\116\101\114")end

local function OnActivation()
	if Player.Character.Humanoid:GetState() == Enum.HumanoidStateType.Swimming then return end
	if CanFire then
		CanFire = false
		
		local rocket = table.remove(Buffer, 1)
		rocket.Rocket.Transparency = 0
		Tool.FireRocket:FireServer(rocket)		
		
		local toMouse = (Mouse.Hit.p - Handle.Position).unit
		local direction = toMouse * 5
		
		rocket.PrimaryPart.CFrame = CFrame.new(Handle.Position, Handle.Position + direction) + direction
		rocket.PrimaryPart.Velocity = direction * 40
		RocketManager:BindRocketEvents(rocket)
		
		wait(Configurations.ReloadTimeSeconds.Value)
		CanFire = true	
	end
end

local function OnStorageAdded(child)
	table.insert(Buffer, child)
end

local function SetupJoints()
	local torso = Player.Character.Torso
	
	Neck = torso.Neck
	OldNeckC0 = Neck.C0
	Shoulder = torso['Right Shoulder']
	OldShoulderC0 = Shoulder.C0
end

local function Frame(mousePosition)
	if Player.Character.Humanoid:GetState() == Enum.HumanoidStateType.Swimming then return end
	local torso = Player.Character.HumanoidRootPart
	local head = Player.Character.Head
	
	local toMouse = (mousePosition - head.Position).unit
	local angle = math.acos(toMouse:Dot(Vector3.new(0,1,0)))
	
	local neckAngle = angle
	
	-- Limit how much the head can tilt down. Too far and the head looks unnatural
	if math.deg(neckAngle) > 110 then
		neckAngle = math.rad(110)
	end
	Neck.C0 = CFrame.new(0,1,0) * CFrame.Angles(math.pi - neckAngle,math.pi,0)
	
	-- Calculate horizontal rotation
	local arm = Player.Character['Right Arm']
	local fromArmPos = torso.Position + torso.CFrame:vectorToWorldSpace(Vector3.new(
		torso.Size.X/2 + arm.Size.X/2, torso.Size.Y/2 - arm.Size.Z/2, 0))
	local toMouseArm = ((mousePosition - fromArmPos) * Vector3.new(1,0,1)).unit
	local look = (torso.CFrame.lookVector * Vector3.new(1,0,1)).unit
	local lateralAngle = math.acos(toMouseArm:Dot(look))
	
	-- Check for rogue math
	if tostring(lateralAngle) == "-1.#IND" then
		lateralAngle = 0
	end		
	
	-- Handle case where character is sitting down
	if Player.Character.Humanoid:GetState() == Enum.HumanoidStateType.Seated then			
		local cross = torso.CFrame.lookVector:Cross(toMouseArm)
		if lateralAngle > math.pi/2 then
			lateralAngle = math.pi/2
		end
		if cross.Y < 0 then
			lateralAngle = -lateralAngle
		end
	end	
	
	-- Turn shoulder to point to mouse
	Shoulder.C0 = CFrame.new(1,0.5,0) * CFrame.Angles(math.pi/2 - angle,math.pi/2 + lateralAngle,0)	
	
	-- If not sitting then aim torso laterally towards mouse
	if Player.Character.Humanoid:GetState() ~= Enum.HumanoidStateType.Seated then
		torso.CFrame = CFrame.new(torso.Position, torso.Position + (Vector3.new(
			mousePosition.X, torso.Position.Y, mousePosition.Z)-torso.Position).unit)
	end	
end

local function MouseFrame()
	Frame(Mouse.Hit.p)
end

local function OnEquip()
	-- Setup joint variables
	SetupJoints()
	
	-- Replace mouse icon and store old
	OldMouseIcon = Mouse.Icon
	Mouse.Icon = 'rbxassetid://79658449'
	
	Mouse.TargetFilter = Player.Character
	
	AutoRotate = Player.Character.Humanoid.AutoRotate
	Player.Character.Humanoid.AutoRotate = false
	
	RunService:BindToRenderStep('RotateCharacter', Enum.RenderPriority.Input.Value, MouseFrame)
end

local function OnUnequip()
	Mouse.Icon = OldMouseIcon
	
	Neck.C0 = OldNeckC0
	Shoulder.C0 = OldShoulderC0
	
	Player.Character.Humanoid.AutoRotate = AutoRotate
	RunService:UnbindFromRenderStep('RotateCharacter')
end
