Я тут недавно подумал что цикл уроков превращает в какую-то микро игру в жанре RPG или выживача. В принципе я люблю и то и другое.
Продолжим. Что надо после того как ресурсы добыл? Сложить их в инвентарь! Вот его то и сделаем сейчас. Мы не будем изгаляться с супер-пупер инвентарём. Стаки ресурсов, ограничители по весу и/или объёму положенного, да и вообще с количеством ячеек. И уж тем более не будем хранить ничего в БД Роблакса и тем более за его пределами. У нас будет обычная фиговина, что будет считать количество ресурсов доступных игроку. Этого будет достаточно, чтобы в последствии сделать «примитивный» крафт предметов.
А по сути, инвентарь это обычная таблица в которой хранятся пары: что — сколько.
Погнали! В нашем скрипте инструмента есть строчки:
if val > 0 then
warn("Получено:", name, val)
end
Вот в этом месте мы и будем добавлять в наш инвентарь что мы добыли. А с учётом того, что у нас скрипт инструмента серверный, то и заморачиваться с проверками (что и сколько добыли и не чит ли это ленивого игрока) мы не будем.
В персонаже хранить нельзя, в workspace — в принципе то же не стоит. Поэтому будем хранить в player — это место которое существует, пока игрок в игре. Но и просто в игроке тоже не стоит, «мусора» может стать ну очень много, поэтому нам нужна папка в игроке. И тут мы сталкиваемся с тем, что в режиме редактирования игры в Studio, мы не можем там разместить папку. Самый примитивный вариант это поместить её StarterPlayer/StarterPlayerScripts, но она будет утоплена в игроке. Второй вариант создать её скриптом на этапе подключения игрока. И я выбираю именно этот вариант.
Возьмём из документации образец подключения игрока и просто вставим там создание папки. Лишнее удалять не будем, оно может нам позже пригодиться. Назовём его — PlayerLoader и поместим в положенное место — ServerScriptService.
-- будет работать при подключении игрока и спавне/респавне персонажей
local Players = game:GetService("Players")
local function onCharacterAdded(character)
print(character.Name .. " has spawned")
end
local function onCharacterRemoving(character)
print(character.Name .. " is despawning")
end
local function onPlayerAdded(player)
player.CharacterAdded:Connect(onCharacterAdded)
player.CharacterRemoving:Connect(onCharacterRemoving)
-- добавить папку инвентаря
local invent = Instance.new("Folder")
invent.Name = "Inventory"
invent.Parent = player
end
Players.PlayerAdded:Connect(onPlayerAdded)

После запуска видим нужную папку.
Что же, теперь вернёмся к нашему скрипту с ресурсами и сохраним, кровно заработанное, в нашем инвентаре. Т.е. просто найдём нужный ресурс в этой папке и увеличим его значение на добытое число. Вот что получается:
if val > 0 then
warn("Получено:", name, val)
local character = script.Parent.Parent -- персонаж
local player = Players:GetPlayerFromCharacter(character) -- игрок
local invent = player:FindFirstChild("Inventory")
if invent then -- инвентарь уже должен быть (это контрольный выстрел)
local saveRes = invent:FindFirstChild(name) -- ищем ресурс
if saveRes == nil then -- если ещё его не считали
saveRes = Instance.new("NumberValue") -- создаём новую запись
saveRes.Name = name
saveRes.Value = 0
saveRes.Parent = invent
end
saveRes.Value = saveRes.Value + val -- обновляем значение
end
end

Запустили и получили что хотели. Теперь добавим это изменение и в кирку. Особо смышлёные могут почитать про module и как подключать функции оттуда, чтобы в каждом инструменте не заниматься копи-пастом. Но у нас всего два инструмента и.. мне всё равно на это сейчас.
Итак, первую часть выполнили — ресурсы считаются и хранятся. Вторая часть будет отобразить инвентарь. Не буду делать ничего красочного (не в этом задача), а просто создадим на экране табличку с текущими составляющими нашего инвентаря. В StarterGui накидаем подобное:

И в его LocalScript поместим следующий код:
local Players = game:GetService("Players")
local player = Players.LocalPlayer
screen = script.Parent -- наш экран
local sf = screen:WaitForChild("ScrollingFrame") -- наше отображение
local sample = sf:WaitForChild("Sample"):Clone() -- заготовка
local ui = sf:WaitForChild("UIListLayout"):Clone() -- размещатель
local invent = player:WaitForChild("Inventory") -- ссылка на инвентарь
while task.wait(.1) do -- бесконечное обновление
sf:ClearAllChildren() -- зачистить от всех элементов
local uic = ui:Clone() -- копия копии UI
uic.Parent = sf -- пихаем в список
for _, res in pairs(invent:GetChildren()) do -- перебираем
local element = sample:Clone() -- копия копии элемента
element.Names.Text = res.Name -- укажем имя
element.Amount.Text = res.Value -- укажем значение
element.Parent = sf -- поместим в список
end
end
Ну и запустим. Побегаем, подолбим и порубим!

Примитивный инвентарь готов.
Ну и собственно сам плейс прилагается, потому как мне очень не хочется писать как сделать GUI…