Menu
CoddyTech

Rarity Rolls

Lesson 10 of 18 in Coddy's Roblox Game: Pet Simulator course.

An egg should not always give a Cat. Settings.Pets lists every pet with a Chance out of 100 (Cat 45, Dog 30, Bunny 15, Fox 8, Dragon 2), a Rarity and a Power.

A weighted roll: pick a number from 0 to 100, then walk down the list taking each pet's chance off it. The pet that takes it to 0 or below wins, so a pet with chance 45 wins 45 rolls in 100 on average:

local roll = math.random() * 100
for _, info in Settings.Pets do
	roll -= info.Chance
	if roll <= 0 then
		return info.Name
	end
end

The hatched pet also carries its Rarity and Power as attributes. A table of the pets by name (petInfo["Fox"]) finds them quickly.

challenge icon

Challenge

Medium
  1. Build petInfo, Settings.Pets keyed by Name.
  2. In givePet, set the pet's Rarity and Power attributes from petInfo.
  3. Write rollPet(), the weighted roll, and hatch rollPet() instead of a Cat (the print names whatever hatched).

Press Play and hatch a few. Then Check: the checks change the chances to make sure your roll follows them.

Try it yourself

local Players = game:GetService("Players")
local ServerStorage = game:GetService("ServerStorage")
local Settings = require(game.ReplicatedStorage.Settings)

local remotes = game.ReplicatedStorage.Remotes
local piles = workspace.Piles
local pileSpot = {} -- each pile -> the spot it stands on
local lastHit = {} -- each player -> when they last hit

print("A Meadow pile gives " .. Settings.PileValue .. " coins")

-- A pet: a StringValue in the player's Pets folder holding its name
local function givePet(player, name)
	local pet = Instance.new("StringValue")
	pet.Name = "Pet"
	pet.Value = name
	pet.Parent = player.Pets
	return pet
end

-- Every player gets Coins on the leaderboard
Players.PlayerAdded:Connect(function(player)
	local leaderstats = Instance.new("Folder")
	leaderstats.Name = "leaderstats"
	leaderstats.Parent = player

	local coins = Instance.new("IntValue")
	coins.Name = "Coins"
	coins.Parent = leaderstats

	-- the pets they own
	local pets = Instance.new("Folder")
	pets.Name = "Pets"
	pets.Parent = player
end)

-- A coin pile on a spot: a copy of ServerStorage.CoinPile with its health
-- and value as attributes
local function spawnPile(spot)
	local pile = ServerStorage.CoinPile:Clone()
	pile.Position = spot.Position
	pile:SetAttribute("MaxHealth", Settings.PileHealth)
	pile:SetAttribute("Health", Settings.PileHealth)
	pile:SetAttribute("Value", Settings.PileValue)
	pile.HealthGui.Label.Text = pile:GetAttribute("Health") .. "/" .. pile:GetAttribute("MaxHealth")
	pileSpot[pile] = spot
	pile.Parent = piles
	return pile
end

-- A hit takes 1 off a pile's health;
-- at 0 the pile breaks and pays its value
local function hitPile(player, pile)
	local health = pile:GetAttribute("Health") - 1
	if health > 0 then
		pile:SetAttribute("Health", health)
		pile.HealthGui.Label.Text = health .. "/" .. pile:GetAttribute("MaxHealth")
		return
	end
	player.leaderstats.Coins.Value += pile:GetAttribute("Value")
	local spot = pileSpot[pile]
	pileSpot[pile] = nil
	pile:Destroy()
	-- a new pile on the same spot, a few seconds later
	task.delay(Settings.RespawnTime, spawnPile, spot)
end

-- A pile on every spot in the Meadow
for _, spot in workspace.Zones.Meadow.Spawns:GetChildren() do
	spawnPile(spot)
end

-- The client asks to hit a pile. Never trust the client: anyone can fire
-- this remote with anything, from anywhere, as fast as they like.
remotes.Hit.OnServerEvent:Connect(function(player, pile)
	-- a real pile
	if typeof(pile) ~= "Instance" or pile.Parent ~= piles then
		return
	end
	-- in reach
	local character = player.Character
	local root = character and character:FindFirstChild("HumanoidRootPart")
	if not root or (root.Position - pile.Position).Magnitude > Settings.Reach then
		return
	end
	-- not too fast
	local now = time()
	if lastHit[player] and now - lastHit[player] < Settings.HitCooldown then
		return
	end
	lastHit[player] = now
	hitPile(player, pile)
end)

-- Hatching: the egg's prompt, paid for in coins
workspace.Egg.ProximityPrompt.Triggered:Connect(function(player)
	local coins = player.leaderstats.Coins
	if coins.Value < Settings.EggPrice then
		return
	end
	coins.Value -= Settings.EggPrice
	local name = "Cat"
	givePet(player, name)
	print(player.Name .. " hatched a " .. name)
end)
quiz iconTest yourself

This lesson includes a short quiz. Start the lesson to answer it and track your progress.

All lessons in Roblox Game: Pet Simulator