Grid Placement System

i have this module right here which is responsible for calculating its block cframe for both client and the server, the problem is that half of the block is submerged (or whatever its called)

i tried adding the primary part y size to the cframe but it has a somewhat glitchy behavior

-- [[ SERVICES ]]

local ReplicatedStorage = game:GetService('ReplicatedStorage')
local UserInputService = game:GetService('UserInputService')
local RunService = game:GetService('RunService')
local Players = game:GetService('Players')

-- [[ MATH FUNCTIONS ]]

local floor = math.floor
local round = math.round

-- [[ MODULE ]]

local Placement = {
	constants = {
		GRID_UNIT = 3;
		MATRICES = {
			BACK = Vector3.new(0, -1, 0);
			TOP = Vector3.new(0, 0, -1);
			RIGHT = Vector3.new(-1, 0, 0);
		};
	}
}

table.freeze(Placement.constants)

function Placement.new(canvas: BasePart)
	local self = setmetatable({}, {__index = Placement})

	self.canvas = canvas;

	return self
end

function Placement:Raycast(mouse: Mouse, params: RaycastParams?)
	local unitRay = mouse.UnitRay
	
	return workspace:Raycast(unitRay.Origin, unitRay.Direction * 1000, params)
end

function Placement:Snap(pos: Vector3): Vector3
	return Vector3.new(
		round(pos.X / self.constants.GRID_UNIT) * self.constants.GRID_UNIT,
		round(pos.Y / self.constants.GRID_UNIT) * self.constants.GRID_UNIT,
		round(pos.Z / self.constants.GRID_UNIT) * self.constants.GRID_UNIT
	)
end

function Placement:GetCFrame(model: Model, position: Vector3, normal: Vector3)
	return CFrame.new(
		self:Snap(position + normal)
	)
end

function Placement:Colliding(model: Model, plot: Instance)	
	local params = OverlapParams.new()
	params.FilterDescendantsInstances = {plot}
	params.FilterType = Enum.RaycastFilterType.Whitelist
	
	local parts = workspace:GetPartsInPart(model.PrimaryPart, params)
	for _, part in parts do
		if not model:IsAncestorOf(part) then
			return true
		end
	end
end

function Placement:Place(...)
	return ReplicatedStorage.Remotes.Place:InvokeServer(...)
end

return Placement

baseplate properties:
image

1 Like

you probably want to modify where the Y value rounds to in the snap function

i dont know what to add to the y position

try

function Placement:Snap(pos: Vector3): Vector3
	return Vector3.new(
		round(pos.X / self.constants.GRID_UNIT) * self.constants.GRID_UNIT,
		(round(pos.Y / self.constants.GRID_UNIT) + .5) * self.constants.GRID_UNIT,
		round(pos.Z / self.constants.GRID_UNIT) * self.constants.GRID_UNIT
	)
end

id just move around the + .5 around there until it works if this one doesnt


it did solve the main issue, but it has the glitchy movement i was talking about

i would just move the baseplate down by .5 then
edit: and revert the function back to normal

i repositioned the baseplate down by .5 and reverted the function back to its original state, nothing seems to change from the original