LineRunnerService

mail@pastecode.io avatar
unknown
lua
a year ago
4.5 kB
2
Indexable
Never
local dataStoreService = game:GetService("DataStoreService")
local highScoreDataService = dataStoreService:GetDataStore("HighScoreDS")


-- where you save the obstacles
local container = Instance.new("Folder", workspace)
container.Name = "Obstacles"


-- Run wherenever Player join the game
game.Players.PlayerAdded:Connect(function(plr)
	-- Create leaderboard

	local ls = Instance.new("Folder", plr)
	ls.Name = "leaderstats"

	local score = Instance.new("IntValue")
	score.Name = "Score"
	score.Parent = ls

	local highScore = Instance.new("IntValue")
	highScore.Name = "High Score"
	highScore.Parent = ls

	-- get saved highscore from Data Stores
	coroutine.resume(coroutine.create(function()

		pcall(function()
			local data = highScoreDataService:GetAsync(plr.UserId .. "-HighScore")

			-- set the value if any data is found, else set it to 0
			highScore.Value = data or 0
		end)
	end))


	plr.CharacterAdded:Connect(function(char)


		-- Clear all obstacles from the container 
		container:ClearAllChildren()


		-- save Player's Z Position as starting position
		local startZ = char.HumanoidRootPart.Position.Z
		local oldZ = startZ

		score.Value = 0


		local stages = 0


		-- Run every frame
		game:GetService("RunService").Heartbeat:Connect(function()

			-- Set the new Z Position to Player's current Z Position
			local newZ = char.HumanoidRootPart.Position.Z
			local ptsIncrease = (newZ - oldZ) * 10

			if ptsIncrease > 0 then score.Value += ptsIncrease end

			oldZ = newZ


			if score.Value > highScore.Value then

				highScore.Value = score.Value
			end
		end)


		while char.Humanoid.Health > 0 do


			if char.HumanoidRootPart.Velocity.Magnitude > 0 or not container:FindFirstChild("10") then

				stages += 1

				-- spawn random stage
				local newStage = script:GetChildren()[math.random(1, #script:GetChildren())]:Clone()
				newStage.Name = stages

				newStage.PrimaryPart = newStage.Start

				if stages > 1 then 
					newStage:SetPrimaryPartCFrame(container[stages - 1].End.CFrame)
				end

				newStage.Parent = container


				for i, child in pairs(newStage:GetChildren()) do


					-- set touch listener, if touching part with name "Kill" then set the Player health to 0

					if child.Name == "Kill" then


						for x, descendant in pairs(child:GetDescendants()) do


							if descendant:IsA("Part") then

								descendant.Touched:Connect(function(touched)


									if touched.Parent:FindFirstChild("Humanoid") then

										touched.Parent.Humanoid.Health = 0
									end
								end)
							end
						end

						-- set touch listener, if touching part with name "Coin" then add Score's Value
					elseif child.Name == "Coin" then


						local bav = Instance.new("BodyAngularVelocity", child)
						bav.MaxTorque = Vector3.new(math.huge, math.huge, math.huge)
						bav.AngularVelocity = Vector3.new(0, 10, 0)

						local bp = Instance.new("BodyPosition", child)
						bp.MaxForce = Vector3.new(math.huge, math.huge, math.huge)
						bp.Position = child.Position

						child.Anchored = false



						child.Touched:Connect(function(touched)

							if game.Players:GetPlayerFromCharacter(touched.Parent) and touched.Parent.Humanoid.Health > 0 then

								child:Destroy()

								score.Value = score.Value + 300
							end
						end)


					elseif child.Name == "End" or child.Name == "Start" then

						child.CanCollide = false
						child.Transparency = 1
					end		
				end

				-- delete the old stage
				coroutine.resume(coroutine.create(function()

					while wait() do

						local zTravelled = char.HumanoidRootPart.Position.Z - startZ
						local stageLength = newStage.End.Position.Z - newStage.Start.Position.Z

						if stageLength * tonumber(newStage.Name) < zTravelled then

							newStage:Destroy()
							break
						end
					end
				end))
			end

			wait(2)
		end
	end)
end)


-- runs whenever Player leave the game
game.Players.PlayerRemoving:Connect(function(plr)

	pcall(function()
		highScoreDataService:SetAsync(plr.UserId .. "-HighScore", plr.leaderstats["High Score"].Value)
	end)
end)


-- runs whenever Player close the game
game:BindToClose(function()

	for i, plr in pairs(game.Players:GetPlayers()) do

		pcall(function()
			highScoreDataService:SetAsync(plr.UserId .. "-HighScore", plr.leaderstats["High Score"].Value)
		end)
	end
end)