I'm trying to make a minecraft building system but it only works on one side!

so i’m tryna make a building system here but as you can see in the video, it only likes to build on one side

what’s the problem here and how do i solve it?
i want the blocks to be placed while facing me (like in minecraft)
this is my code that raycasts from the camera then uses a function to round it to the nearest 4th stud which is placed in startercharacterscripts.

local RS = game:GetService("RunService")
local Camera = game.Workspace.CurrentCamera
script.Parent.Archivable = true
local outline = game.ReplicatedStorage.Visuals.HoverOutline

local raycast = function()
	local camera = workspace.CurrentCamera
	local cameraCF = camera.CFrame

	local length = 24
	local params = RaycastParams.new()
	params.FilterType = Enum.RaycastFilterType.Exclude
	params.FilterDescendantsInstances = { script.Parent, game.Workspace.Blocks:FindFirstChild("PlaceTestBlock")}

	local raycastResult = workspace:Raycast(cameraCF.Position, cameraCF.LookVector * length, params)
	if raycastResult then
		return raycastResult
	else
		return nil
	end
end

local function roundToStep(initialValue,step)
	local roundedValue = math.floor(initialValue/step)*step
	return roundedValue --Returns 60
end

UIS.InputBegan:Connect(function(input, gameProcessed)
	if input.UserInputType == Enum.UserInputType.MouseButton1 then
		print("break")
		local raycastResult = raycast()
		if not raycastResult then return end
		
		if raycastResult.Instance.Parent == game.Workspace.Blocks then
			raycastResult.Instance:Destroy()
		end
	end
end)
UIS.InputBegan:Connect(function(input, gameProcessed)
	if input.UserInputType == Enum.UserInputType.MouseButton2 then
		print("place")
		local raycastResult = raycast()
		if not raycastResult then return end

		local newBlock = game.ReplicatedStorage.Blocks.TestBlock:Clone()
		newBlock.Anchored = true
		newBlock.Parent = game.Workspace.Blocks
		local raycastPosition = raycastResult.Position
		newBlock.Position = game.Workspace.Blocks:FindFirstChild("PlaceTestBlock").Position
		
	end
end)

RS.RenderStepped:Connect(function()
	if game.Workspace.Blocks:FindFirstChild("PlaceTestBlock") then
		game.Workspace.Blocks:FindFirstChild("PlaceTestBlock"):Destroy()
	end
	local raycastResult = raycast()
	if raycastResult == nil then
		return
	end
	local newBlock = game.ReplicatedStorage.Blocks.PlaceTestBlock:Clone()
	newBlock.Anchored = true
	newBlock.Parent = game.Workspace.Blocks
	local raycastPosition = raycastResult.Position

	newBlock.Position = Vector3.new(roundToStep(raycastPosition.X, 4), roundToStep(raycastPosition.Y, 4), roundToStep(raycastPosition.Z, 4)) + Vector3.new(2, 2, 2)

	
	if raycastResult.Instance.Parent == game.Workspace.Blocks then
		outline.Parent = raycastResult.Instance
	else
		outline.Parent = game.ReplicatedStorage.Visuals
	end
end)
4 Likes

I was messing around with your code and I think I found a solution:

local raycastPosition = raycastResult.Position
local bumpedPosition = raycastPosition + 2*raycastResult.Normal
	newBlock.Position = Vector3.new(roundToStep(bumpedPosition .X, 4), roundToStep(bumpedPosition .Y, 4), roundToStep(bumpedPosition .Z, 4)) + Vector3.new(2, 2, 2)

this is how I think it works:
image
It brings the position closer to where you want the block to be so it rounds to where you want it instead of inside the block that’s already there.

2 Likes

very helpful thanks i think this would work but over that time i watched 40 minutes worth of this and this and got the system working myself. thanks! i will mark this as a solution

1 Like

This topic was automatically closed 14 days after the last reply. New replies are no longer allowed.