Hey there! I am trying to make a loot box system using this video tutorial:
and I wrote everything out and I came across a couple bugs.
Item Module Script in ReplicatedStorage:
local m = {}
m.Rarities = {
{
name = "Legendary";
rarity = 0.05;
color = Color3.fromRGB(170, 0, 255);
};
{
name = "Epic";
rarity = 0.15;
color = Color3.fromRGB(255, 0, 0);
};
{
name = "Very Rare";
rarity = 0.3;
color = Color3.fromRGB(255, 170, 0);
};
{
name = "Rare";
rarity = 0.5;
color = Color3.fromRGB(255, 255, 0);
};
{
name = "Uncommon";
rarity = 0.7;
color = Color3.fromRGB(0, 170, 255);
};
{
name = "Common";
rarity = 0.9;
color = Color3.fromRGB(0, 255, 0);
};
}
m.Cases = {
Classic = {
items = {
"Green Trail";
"Blue Trail";
"Yellow Trail";
"Orange Trail";
"Red Trail";
"Purple Trail";
}
}
}
m.Items = {
{
name = "Green Trail";
imageID = "6128040883";
rarityType = "Common"
};
{
name = "Blue Trail";
imageID = "6128041800";
rarityType = "Uncommon"
};
{
name = "Yellow Trail";
imageID = "6128038485";
rarityType = "Rare"
};
{
name = "Orange Trail";
imageID = "6128040179";
rarityType = "Very Rare"
};
{
name = "Red Trail";
imageID = "6128037610";
rarityType = "Epic"
};
{
name = "Purple Trail";
imageID = "6128039197";
rarityType = "Legendary"
};
}
return m
case Module Script in the StarterGui
local m = {}
local items = require(game.ReplicatedStorage.Items)
local player = game.Players.LocalPlayer
local gui = player:WaitForChild("PlayerGui")
local ui = gui:WaitForChild("SpeedGUI")
local elements = gui:WaitForChild("Elements")
function m:getRarity(type)
for a, b in ipairs(items.Rarities) do
if b.name == type then
return b
end
end
end
function m:createItem()
--Clone object and Set Scaleable Properties
local object = elements:WaitForChild("item"):Clone()
local scaledSize = math.floor((object.Size.X.Scale * m.settings.cUI.AbsoluteSize.Y)+0.5)/m.settings.cUI.AbsoluteSize.X
--Get and Set Types
local types = {}
for a,b in ipairs(m.settings.case.items) do
for d,c in ipairs(items.Items) do
if c.name == b then
local r = m:getRarity(c.rarityType)
for t = 1, r.rarity*10 do
table.insert(types,c)
end
end
end
end
--Select item
local item = types[m.settings.prng:NextInteger(1,#types)]
local itemType = m:getRarity(item.rarityType)
--Set other properties
object.BorderColor3 = itemType.color
object.rarityMark.BackgroundColor3 = itemType.color
object.rarityMark.rarity.Text = itemType.name
object.Name = item.name
object.itemImage.Image = "rbxassetid://" .. item.imageID
--Set Position
object.Position = (m.settings.lastObject and m.settings.lastObject.Position + UDim2.new(scaledSize,0,0,0) + m.settings.offset) or UDim2.new(-scaledSize/2,0,0.5,0)
--Set Parent
object.Parent = m.settings.cUI
--Set few variables
m.settings.lastObject = object
table.insert(m.settings.objects, object)
end
function m:check()
for a,b in ipairs(m.settings.objects) do
local scaledSize = b.AbsoluteSize
if b.AbsolutePosition.X <= -scaledSize.x+m.settings.offset.X.Offset then
table:remove(m.settings.objects,a)
b:Destroy()
m:createItem()
m:check()
end
end
end
function m:update()
m.settings.speed = math.max(m.settings.speed-(0.03/m.settings.spinLength),0)
m.settings.newAccel = m.settings.accel*math.sin((math.pi/2)*m.settings.speed)
for a,b in ipairs(m.settings.objects) do
b.Position = b.Position - UDim2.new(m.settings.newAccel/m.settings.cUI.AbsoluteSize.X,0,0,0)
end
if m.settings.newAccel == 0 then
m:result()
end
end
function m:result()
--Disconnect
m.render:disconnect()
--Get selected item
local item = nil
for a,b in ipairs(m.settings.objects) do
local left,right = b.AbsolutePosition.X/m.settings.cUI.AbsoluteSize.X,
(b.AbsolutePosition.X + b.AbsoluteSize.X)/m.settings.cUI.AbsoluteSize.X
if left <= 0.5 and right >= 0.5 then
item = b
break
end
end
if item then
m.newResult = item
else
local closestItems = {}
for a,b in ipairs(m.settings.objects) do
table.insert(closestItems {
mag = (Vector2.new(b.AbsolutePosition.X/m.settings.cUI.AbsoluteSize.X,0)-Vector2.new(0.5,0)).magnitude;
item = b;
})
end
table.sort(closestItems,function(a,b) return a.mag<b.mag end)
m.newResult = closestItems[1].item
end
end
function m:create(caseType)
--Settings
m.settings = {
case = items.Cases[caseType];
cUI = elements:WaitForChild("caseUI"):Clone();
objects = {};
prng = Random.new();
offset = UDim2.new(0,25,0,0);
accel = 30;
speed = 1;
spinLength = 5;
}
m.newResult = nil
--PreSetup
m.settings.cUI.Parent = ui
for t = 1, 15 do
m:createItem()
end
--Services
m.render = game:GetService("RunService").RenderStepped:connect(function()
m:update()
m:check()
end)
--Wait for result
repeat wait() until m.newResult
--Get rid of ui
spawn(function()
wait(1)
m.settings.cUI:TweenPosition(UDim2.new(0,0,1.15,0),"Out", "Sine", 1, true, function() m.settings.cUI:Destroy() end)
end)
return m.newResult
end
return m
Client local script in the StarterGui
local a = require(game.Players.LocalPlayer:WaitForChild("PlayerGui").Modules.case):create("Classic")
print(a)
Pic of the explorer:
This is the error I am getting,
Line 62 and 133 are in the case script here
function m:check()
for a,b in ipairs(m.settings.objects) do
local scaledSize = b.AbsoluteSize
if b.AbsolutePosition.X <= -scaledSize.x+m.settings.offset.X.Offset then
table:remove(m.settings.objects,a) --This line is throwing the error
b:Destroy()
m:createItem()
m:check()
end
end
end
m.render = game:GetService("RunService").RenderStepped:connect(function()
m:update()
m:check() --This line fires the function
end)
This scripting is a little advanced for me and I don’t understand everything, so does anyone have any idea why I am getting that error. Isn’t “a”(or argument #2) inherently a number? Not a table?