Recently I've been trying to make a block generation system similar to Mining Simulator's for a game. The idea of the code is to make blocks spawn around a block that was mined but obviously not spawn them where blocks already are. To do this I save the position of the blocks already existing, ones that are mined, and ones that are made. But the problem I run into is that the code constantly ignores the fact they're not supposed to spawn there and does it anyway.
local ServerStorage = game:GetService("ServerStorage") local blockData = ServerStorage:WaitForChild("blockData") function BackTrack(Target,Pos) Target.Parent = workspace.Mineable Target.CFrame = Pos if blockData:FindFirstChild(tostring(Target.CFrame)) then Target:Destroy() end Instance.new("Folder",blockData).Name = tostring(Target.CFrame) end function CreateBlocks(Target) local bpos = Target.CFrame Instance.new("Folder",blockData).Name = tostring(bpos) spawn(function() BackTrack(ReplicatedStorage.Blocks.Dirt.Block:Clone(),CFrame.new(bpos.X,bpos.Y-7,bpos.Z)) end) spawn(function() BackTrack(ReplicatedStorage.Blocks.Dirt.Block:Clone(),CFrame.new(bpos.X,bpos.Y,bpos.Z+7)) end) spawn(function() BackTrack(ReplicatedStorage.Blocks.Dirt.Block:Clone(),CFrame.new(bpos.X,bpos.Y,bpos.Z-7)) end) spawn(function() BackTrack(ReplicatedStorage.Blocks.Dirt.Block:Clone(),CFrame.new(bpos.X+7,bpos.Y,bpos.Z)) end) spawn(function() BackTrack(ReplicatedStorage.Blocks.Dirt.Block:Clone(),CFrame.new(bpos.X-7,bpos.Y,bpos.Z)) end) spawn(function() BackTrack(ReplicatedStorage.Blocks.Dirt.Block:Clone(),CFrame.new(bpos.X,bpos.Y+7,bpos.Z)) end) end
To debug this problem, you should generate just a few blocks so you can look through the names and CFrames of everything to determine why that blockData:FindFirstChild
line isn't working the way you expect it to. I have a few suspicions as to why that might happen:
* If you initially spawn your parts in with any rotation at all, the CFrames won't match (you should consider using tostring(Target.Position)
instead of .CFrame)
* If the position isn't made up of integers (with absolutely no decimals), perhaps some arithmetic inaccuracies are causing slightly different tostring
results (ex the difference between 0.99999 and 1).
Also, you can improve your code by checking for the part before cloning (and then potentially destroying it):
local ServerStorage = game:GetService("ServerStorage") local blockData = ServerStorage:WaitForChild("blockData") local function MaybeAddBlock(originalBlock, pos) -- where 'pos' is a Vector3 local name = tostring(pos) if blockData:FindFirstChild(name) then return end local newBlock = originalBlock:Clone() newBlock.CFrame = CFrame.new(pos) newBlock.Parent = workspace.Mineable -- parent things after setting other properties for best performance local folder = Instance.new("Folder") folder.Name = name folder.Parent = blockData end local dist = 7 local relativePositions = { Vector3.new(-dist, 0, 0), Vector3.new(dist, 0, 0), Vector3.new(0, -dist, 0), Vector3.new(0, dist, 0), Vector3.new(0, 0, -dist), Vector3.new(0, 0, dist), } local dirt = ReplicatedStorage.Blocks.Dirt.Block local function CreateBlocks(target) for _, relativePos in ipairs(relativePositions) do MaybeAddBlock(dirt, target.Position + relativePos) end end