What do you mean by ‘make part bla bla’?
the process of making a part
It means inserting a new part by Instance.new()
or cloning a part
It has very tutorials on yt, showing make like minecraft system.
search placement system
I get it. You’re trying to make a building system, something like Piggy: Build mode?
@Qinrir and @AridFights1 Now I understand! But how do you make like an inventory with different blocks, and you can select it and place?
i Did Made A Minecraft Like game but Never was Able To Make Inventory
There are multiple ways of making a grid placement system.
Here are some:
also not to mention if you do grid placement sometime it break meaning when you click in the negative axis the code dosent work as intended to it places the part in another part the way around this is lengthy
just a bit of info, you can lock it to a grid by doing
vector3.new(math.ceil(position.x/3), math.ceil(position.y/3), math.ceil(position.z/3))*3
to get the block normal via a camera raycast you can use this function
(mouse.hit.position is good and all but this gives a concrete ignore list)
local UIS = game:GetService("UserInputService")
function RaycastToScreenPos(screenpos, ignorelist, ignoretype)
local camray = workspace.CurrentCamera:ScreenPointToRay(screenpos.x, screenpos.y)
local CastInfo = RaycastParams.new()
CastInfo.FilterType = ignoretype or Enum.RaycastFilterType.Blacklist
--blacklist ignores all in your ignore list, whitelist only goes for the ones in the list
CastInfo.FilterDescendantsInstances = ignorelist or {}
local NewRayResult = workspace:Raycast(camray.Position, camray.Direction * 100000, CastInfo)
--long ray
return NewRayResult
end
local result = RaycastToScreenPos(UIS:GetMouseLocation(), {--[[stuff to ignore goes in here]] }, Enum.RaycastFilterType.Blacklist)
result.Normal = direction of the face you hit (normal)
result.Instance = the part you hit
result.Position = the position of your hit
result.Material = the material of what you hit
putting this all together you can make a placement system with this function in a serverscript
local TemplateContainer = folder where you keep your block templates
local BlocksFolder = folder where blocks are put in Workspace
local PlaceBlockRemote = place block remote
function PlaceBlock(plr, templatename, Normal, Position, hitinst)
local Block = TemplateContainer:FindFirstChild(templatename):Clone()
Block.Position = hitinst.Position+Normal.Unit*3
Block.Parent = BlocksFolder
end
PlaceBlockRemote.OnServerEvent:Connect(function(plr, templatename, Normal, Pos, Hitinst)
--put your checks here
PlaceBlock(plr, templatename, Normal, Pos, Hitinst)
end)
above is easily hackable by firing a remote, add some server checks (ie if player is in range, if player has enough blocks in slot, etc)
and you need the placement system for client
local UIS = game:GetService("UserInputService")
local PlacementRemote = remote for placement
function RaycastToScreenPos(screenpos, ignorelist, ignoretype)
local camray = workspace.CurrentCamera:ScreenPointToRay(screenpos.x, screenpos.y)
local CastInfo = RaycastParams.new()
CastInfo.FilterType = ignoretype or Enum.RaycastFilterType.Blacklist
--blacklist ignores all in your ignore list, whitelist only goes for the ones in the list
CastInfo.FilterDescendantsInstances = ignorelist or {}
local NewRayResult = workspace:Raycast(camray.Position, camray.Direction * 100000, CastInfo)
--long ray
return NewRayResult
end
function PlaceBlock()
local result = RaycastToScreenPos(UIS:GetMouseLocation(), {--[[stuff to ignore goes in here]] }, Enum.RaycastFilterType.Blacklist)
--im not going to add ghost blocks because i have worked on this for a bit longer than i would have liked to
PlacementRemote:FireServer("TemplateName(set this to template name)", result.Normal, result.Position, result.Instance)
end
--bind above to mouse button click or smth
this is just concept code and im not 100% sure it will work. hopefully it will tho
aaaaaaaaaaaaaaaaaaaaaaand Done! @OhLordiez
Done This Works Just As Old Minecraft
local Mouse = game.Players.LocalPlayer:GetMouse()
local function RoundDown(X)
return Vector3.new(math.floor(X.X),math.floor(X.Y),math.floor(X.Z))
end
Mouse.Button1Down:Connect(function()
local snap = 3 -- Grid
local Surface = Mouse.TargetSurface
local Pos = Mouse.Hit.p
if Surface == Enum.NormalId.Top then
Pos = Pos + Vector3.new(0, snap, 0)
elseif Surface == Enum.NormalId.Bottom then
Pos = Pos - Vector3.new(0, snap, 0)
elseif Surface == Enum.NormalId.Left then
Pos = Pos - Vector3.new(snap, 0, 0)
elseif Surface == Enum.NormalId.Right then
Pos = Pos + Vector3.new(snap, 0, 0)
elseif Surface == Enum.NormalId.Front then
Pos = Pos - Vector3.new(0, 0, snap)
elseif Surface == Enum.NormalId.Back then
Pos = Pos + Vector3.new(0, 0, snap)
end
Pos = RoundDown(Pos)
local Part =Instance.new("Part",game.Workspace)
Part.Anchored = true
Part.Size = Vector3.new(3,3,3)
Part.Position = Pos
end)
Also I Didnt Made It For Server Meaning Only You Can See Blocks For Server Sided I Leave It Upon You As Its Not That Hard
Sorry to say but it only works on one axis
You can make an event, so that when you click then you can fire a remote event.
yea i know but i was actually busy too and had to do it as quick as i can thats why i didnt added server sorry for that
still use the camera raycast code instead of mouse.hit.p
because it gives way better ignore list capabilities
edit: plus the entire mouse object is depreciated anyway and not meant to be used in new work
if statements can do that
true
no they don’t, if you do mouse.hit you can have an ignore list but its only one folder