Box on Box cutting system

After making a thread asking about CSG i decided to just try and make my own code for this. This will allow you to cut rectangles from rectangles axis aligned on the X, Y, Z axis. I spent a solid amount of time and I think this could help a lot of people! (This isn’t done and i will be updating this with a revised version)

local RealObject = game.Workspace.Part1
local RealSubtractor = game.Workspace.Subtractor

local Part
local Position = RealObject.Position
local SubtractorPosition = RealObject.Position
local Model = Instance.new("Model")
Model.Name = "CuttingModel"
Model.Parent = game.Workspace

local AlignmentPart = Instance.new("Part")
AlignmentPart.Anchored = true
AlignmentPart.CanTouch = false
AlignmentPart.CanCollide = false
AlignmentPart.Transparency = 1
AlignmentPart.Position = Vector3.new(10000, 100, 10000)

local TempObject = Instance.new("Part")
TempObject.Parent = Model
TempObject.Size = RealObject.Size
TempObject.CFrame = RealObject.CFrame
TempObject.CanCollide = false
TempObject.CanTouch = false
TempObject.Transparency = 1
TempObject.Anchored = true
TempObject.Name = "TempObject"

local TempSubtractor = Instance.new("Part")
TempSubtractor.Parent = Model
TempSubtractor.Size = RealSubtractor.Size
TempSubtractor.CFrame = RealSubtractor.CFrame
TempSubtractor.CanCollide = false
TempSubtractor.CanTouch = false
TempSubtractor.Anchored = true
TempSubtractor.Transparency = 1
TempSubtractor.Name = "TempSubtractor"
Model.PrimaryPart = TempObject
local OrientX
local OrientY
local OrientZ

Model:SetPrimaryPartCFrame(AlignmentPart.CFrame) 
AlignmentPart:Destroy()
TempSubtractor.Orientation = Vector3.new(0, 0, 0)
local Object = TempObject
local Subtractor = TempSubtractor
local Coord1RightX = Object.CFrame.X + Object.Size.X / 2
local Coord2RightX = Subtractor.CFrame.X + Subtractor.Size.X / 2
local CoordRightX = Coord1RightX - Coord2RightX

local Coord1LeftX = Object.CFrame.X - Object.Size.X / 2
local Coord2LeftX = Subtractor.CFrame.X - Subtractor.Size.X / 2
local CoordLeftX =	Coord2LeftX - Coord1LeftX


local Coord1TopY = Object.CFrame.Y + Object.Size.Y / 2
local Coord2TopY = Subtractor.CFrame.Y + Subtractor.Size.Y / 2
local CoordTopY = Coord1TopY - Coord2TopY

local Coord1BottomY = Object.CFrame.Y - Object.Size.Y / 2
local Coord2BottomY = Subtractor.CFrame.Y - Subtractor.Size.Y / 2
local CoordBottomY = Coord2BottomY - Coord1BottomY


local Coord1RightZ = Object.CFrame.Z + Object.Size.Z / 2
local Coord2RightZ = Subtractor.CFrame.Z + Subtractor.Size.Z / 2
local CoordRightZ = Coord1RightZ - Coord2RightZ

local Coord1LeftZ = Object.CFrame.Z - Object.Size.Z / 2
local Coord2LeftZ = Subtractor.CFrame.Z - Subtractor.Size.Z / 2
local CoordLeftZ = Coord2LeftZ - Coord1LeftZ
	
	local PartZLeft
	local PartZRight
	

local PartXLeft = Instance.new("Part")
PartXLeft.Parent = Model
PartXLeft.Anchored = true
PartXLeft.Size = Vector3.new(CoordLeftX, Object.Size.Y, Object.Size.Z)
PartXLeft.CFrame = Object.CFrame * CFrame.new(-((Object.Size.X / 2) - PartXLeft.Size.X/2), 0, 0)

PartXLeft.Transparency = RealObject.Transparency
PartXLeft.Material = RealObject.Material
PartXLeft.Color = RealObject.Color
PartXLeft.TopSurface = RealObject.TopSurface
PartXLeft.BottomSurface = RealObject.BottomSurface
PartXLeft.LeftSurface = RealObject.LeftSurface
PartXLeft.RightSurface = RealObject.RightSurface
PartXLeft.FrontSurface = RealObject.FrontSurface
PartXLeft.BackSurface = RealObject.BackSurface
for i, v in pairs(RealObject:GetChildren()) do
	local Clone = v:Clone()
	Clone.Parent = PartXLeft
end

	if PartXLeft.Size.X >= Object.Size.X then
		PartXLeft.Size = Vector3.new(Object.Size.X, PartXLeft.Size.Y, PartXLeft.Size.Z)
		PartXLeft.Position = Vector3.new(Object.Position.X, PartXLeft.Position.Y, PartXLeft.Position.Z)
	end	
	
local PartXRight = Instance.new("Part")
PartXRight.Parent = Model
PartXRight.Anchored = true
PartXRight.Size = Vector3.new(CoordRightX, Object.Size.Y, Object.Size.Z)
PartXRight.CFrame = Object.CFrame * CFrame.new(((Object.Size.X / 2) - PartXRight.Size.X/2), 0, 0)

PartXRight.Transparency = RealObject.Transparency
PartXRight.Material = RealObject.Material
PartXRight.Color = RealObject.Color
PartXRight.TopSurface = RealObject.TopSurface
PartXRight.BottomSurface = RealObject.BottomSurface
PartXRight.LeftSurface = RealObject.LeftSurface
PartXRight.RightSurface = RealObject.RightSurface
PartXRight.FrontSurface = RealObject.FrontSurface
PartXRight.BackSurface = RealObject.BackSurface

for i, v in pairs(RealObject:GetChildren()) do
	local Clone = v:Clone()
	Clone.Parent = PartXRight
end

	if PartXRight.Size.X >= Object.Size.X then
		PartXRight.Size = Vector3.new(Object.Size.X, PartXRight.Size.Y, PartXRight.Size.Z)
		PartXRight.Position = Vector3.new(Object.Position.X, PartXRight.Position.Y, PartXRight.Position.Z)
	end	
	
if PartXRight.Size.X < 0.05 or PartXLeft.Size.Z < 0.05 then
	PartXRight:Destroy()
end
if PartXLeft.Size.X < 0.05 or PartXLeft.Size.Z < 0.05 then
	PartXLeft:Destroy()
end

if PartXRight ~= nil then

PartZLeft = Instance.new("Part")
	PartZLeft.Parent = Model
	PartZLeft.Anchored = true
	PartZLeft.Size = Vector3.new(Object.Size.X - (PartXLeft.Size.X + PartXRight.Size.X), Object.Size.Y, CoordLeftZ)
		PartZLeft.CFrame = PartXRight.CFrame * CFrame.new((-PartXRight.Size.X/2) - PartZLeft.Size.X/2, 0, -((Object.Size.Z / 2) - PartZLeft.Size.Z/2))
	

	PartZLeft.Transparency = RealObject.Transparency
	PartZLeft.Material = RealObject.Material
	PartZLeft.Color = RealObject.Color
	PartZLeft.TopSurface = RealObject.TopSurface
	PartZLeft.BottomSurface = RealObject.BottomSurface
	PartZLeft.LeftSurface = RealObject.LeftSurface
	PartZLeft.RightSurface = RealObject.RightSurface
	PartZLeft.FrontSurface = RealObject.FrontSurface
	PartZLeft.BackSurface = RealObject.BackSurface
	for i, v in pairs(RealObject:GetChildren()) do
		local Clone = v:Clone()
		Clone.Parent = PartZLeft
	end 
	
	PartZRight = Instance.new("Part")
	PartZRight.Parent = Model
	PartZRight.Anchored = true
	PartZRight.Size = Vector3.new(Object.Size.X - (PartXLeft.Size.X + PartXRight.Size.X), Object.Size.Y, CoordRightZ)
	PartZRight.CFrame = PartXRight.CFrame * CFrame.new((-PartXRight.Size.X/2) - PartZRight.Size.X/2, 0, ((Object.Size.Z / 2) - PartZRight.Size.Z/2))
	

	PartZRight.Transparency = RealObject.Transparency
	PartZRight.Material = RealObject.Material
	PartZRight.Color = RealObject.Color
	PartZRight.TopSurface = RealObject.TopSurface
	PartZRight.BottomSurface = RealObject.BottomSurface
	PartZRight.LeftSurface = RealObject.LeftSurface
	PartZRight.RightSurface = RealObject.RightSurface
	PartZRight.FrontSurface = RealObject.FrontSurface
	PartZRight.BackSurface = RealObject.BackSurface

	for i, v in pairs(RealObject:GetChildren()) do
		local Clone = v:Clone()
		Clone.Parent = PartZRight
	end
		
		if PartZLeft.Size.Z >= Object.Size.Z then
			PartZLeft.Size = Vector3.new(PartZLeft.Size.X, PartZLeft.Size.Y, Object.Size.Z)
			PartZLeft.Position = Vector3.new(PartZLeft.Position.X, PartZLeft.Position.Y, Object.Position.Z)
		end	
		if PartZRight.Size.Z >= Object.Size.Z then
			PartZRight.Size = Vector3.new(PartZRight.Size.X, PartZRight.Size.Y, Object.Size.Z)
			PartZRight.Position = Vector3.new(PartZRight.Position.X, PartZRight.Position.Y, Object.Position.Z)
		end		
		
		
		
	if PartZRight.Size.X < 0.05 or PartZRight.Size.Z < 0.05 then
		PartZRight:Destroy()
	end
	if PartZLeft.Size.X < 0.05 or PartZLeft.Size.Z < 0.05 then
		PartZLeft:Destroy()
	end
elseif PartXLeft ~= nil then
	
PartZLeft = Instance.new("Part")
	PartZLeft.Parent = Model
		PartZLeft.Anchored = true
	
		
	PartZLeft.Size = Vector3.new(Object.Size.X - (PartXLeft.Size.X + PartXRight.Size.X), Object.Size.Y, CoordLeftZ)
		PartZLeft.CFrame = PartXRight.CFrame * CFrame.new(PartXLeft.Size.X/2, 0, -((Object.Size.Z / 2) - PartZLeft.Size.Z/2))
	
	PartZLeft.Transparency = RealObject.Transparency
	PartZLeft.Material = RealObject.Material
	PartZLeft.Color = RealObject.Color
	PartZLeft.TopSurface = RealObject.TopSurface
	PartZLeft.BottomSurface = RealObject.BottomSurface
	PartZLeft.LeftSurface = RealObject.LeftSurface
	PartZLeft.RightSurface = RealObject.RightSurface
	PartZLeft.FrontSurface = RealObject.FrontSurface
	PartZLeft.BackSurface = RealObject.BackSurface
	for i, v in pairs(RealObject:GetChildren()) do
		local Clone = v:Clone()
		Clone.Parent = PartZLeft
	end 
	
PartZRight = Instance.new("Part")
	PartZRight.Parent = Model
	PartZRight.Anchored = true
	PartZRight.Size = Vector3.new(Object.Size.X - (PartXLeft.Size.X + PartXRight.Size.X), Object.Size.Y, CoordRightZ)
	PartZRight.CFrame = PartXRight.CFrame * CFrame.new(PartXLeft.Size.X/2, 0, ((Object.Size.Z / 2) - PartZRight.Size.Z/2))
	
	PartZRight = Instance.new("Part")
	PartZRight.Parent = Model
	PartZRight.Anchored = true
	PartZRight.Size = Vector3.new(Object.Size.X - (PartXLeft.Size.X + PartXRight.Size.X), Object.Size.Y, CoordRightZ)
	PartZRight.CFrame = PartXRight.CFrame * CFrame.new((-PartXRight.Size.X/2) - PartZRight.Size.X/2, 0, ((Object.Size.Z / 2) - PartZRight.Size.Z/2))


	PartZRight.Transparency = RealObject.Transparency
	PartZRight.Material = RealObject.Material
	PartZRight.Color = RealObject.Color
	PartZRight.TopSurface = RealObject.TopSurface
	PartZRight.BottomSurface = RealObject.BottomSurface
	PartZRight.LeftSurface = RealObject.LeftSurface
	PartZRight.RightSurface = RealObject.RightSurface
	PartZRight.FrontSurface = RealObject.FrontSurface
	PartZRight.BackSurface = RealObject.BackSurface
	
	for i, v in pairs(RealObject:GetChildren()) do
		local Clone = v:Clone()
		Clone.Parent = PartZRight
	end 

	
	if PartZRight.Size.X < 0.05 or PartZRight.Size.Z < 0.05 then
		PartZRight:Destroy()
	end
	if PartZLeft.Size.X < 0.05 or PartZLeft.Size.Z < 0.05 then
		PartZLeft:Destroy()
	end
end

local PartYBottom = Instance.new("Part")
PartYBottom.Parent = Model
	PartYBottom.Anchored = true

PartYBottom.Transparency = RealObject.Transparency
PartYBottom.Material = RealObject.Material
PartYBottom.Color = RealObject.Color
PartYBottom.TopSurface = RealObject.TopSurface
PartYBottom.BottomSurface = RealObject.BottomSurface
PartYBottom.LeftSurface = RealObject.LeftSurface
PartYBottom.RightSurface = RealObject.RightSurface
PartYBottom.FrontSurface = RealObject.FrontSurface
PartYBottom.BackSurface = RealObject.BackSurface

for i, v in pairs(RealObject:GetChildren()) do
	local Clone = v:Clone()
	Clone.Parent = PartYBottom
end 


	local PartYTop = Instance.new("Part")
PartYTop.Parent = Model
	PartYTop.Anchored = true	

PartYTop.Transparency = RealObject.Transparency
PartYTop.Material = RealObject.Material
PartYTop.Color = RealObject.Color
PartYTop.TopSurface = RealObject.TopSurface
PartYTop.BottomSurface = RealObject.BottomSurface
PartYTop.LeftSurface = RealObject.LeftSurface
PartYTop.RightSurface = RealObject.RightSurface
PartYTop.FrontSurface = RealObject.FrontSurface
PartYTop.BackSurface = RealObject.BackSurface

for i, v in pairs(RealObject:GetChildren()) do
	local Clone = v:Clone()
	Clone.Parent = PartYTop
end 


	local XNeg = (Object.Position.X - Subtractor.Position.X)
	local ZNeg = (Object.Position.Z - Subtractor.Position.Z)
	local X
	local Z
	local ScalingX
	local ScalingZ
	if PartXRight == nil and PartXLeft == nil then
		ScalingX = Object.Size.X
	else
		
		local XLeft = 0
		local XRight = 0
		if PartXLeft then
			XLeft = PartXLeft.Size.X
		end
		if PartXRight then
			XRight = PartXRight.Size.X
		end
		ScalingX = Object.Size.X - (XLeft + XRight)
	end
	if PartZRight == nil and PartZLeft == nil then
		ScalingZ = Object.Size.Z
	else
		
		local ZLeft = 0
		local ZRight = 0
		if PartXLeft then
			ZLeft = PartZLeft.Size.Z
		end
		if PartXRight then
			ZRight = PartZRight.Size.Z
		end
		
		ScalingZ = Object.Size.Z - (ZLeft + ZRight)
	end
	PartYBottom.Size = Vector3.new(ScalingX, CoordBottomY, ScalingZ) 
	PartYTop.Size = Vector3.new(ScalingX, CoordTopY, ScalingZ) 
	if XNeg < 0 then
		X = -Object.Position.X + ((Subtractor.Position.X - Subtractor.Size.X/2) + PartYBottom.Size.X/2)
	else
		X = -Object.Position.X + ((Subtractor.Position.X + Subtractor.Size.X/2) - PartYBottom.Size.X/2)
	end
	if ZNeg < 0 then
		Z = -Object.Position.Z + ((Subtractor.Position.Z - Subtractor.Size.Z/2) + PartYBottom.Size.Z/2)
	else
		Z = -Object.Position.Z + ((Subtractor.Position.Z + Subtractor.Size.Z/2) - PartYBottom.Size.Z/2)
	end
	
	PartYBottom.Position = Object.Position + Vector3.new(X, (PartYBottom.Size.Y/2 - (Object.Size.Y / 2)), Z) 
	if PartYBottom.Size.X < 0.05 or PartYBottom.Size.Z < 0.05 or PartYBottom.Size.Y < 0.05 then
		PartYBottom:Destroy()
	end
	
	 PartYTop.Position = Object.Position + Vector3.new(X, (-PartYTop.Size.Y/2 + (Object.Size.Y / 2)), Z)  
	if PartYTop.Size.X < 0.05 or PartYTop.Size.Z < 0.05 or PartYTop.Size.Y < 0.05 then
		PartYTop:Destroy()
	end
	if PartYBottom then
		if PartYBottom.Size.Y >= Object.Size.Y then
			PartYBottom.Size = Vector3.new(PartYBottom.Size.X, Object.Size.Y, PartYBottom.Size.Z)
			PartYBottom.Position = Vector3.new(PartYBottom.Position.X, Object.Position.Y, PartYBottom.Position.Z)
		end	
		
		if PartYTop.Size.X + 0.01 >= Object.Size.X then
			PartYTop.Size = Vector3.new(Object.Size.X, PartYTop.Size.Y, PartYTop.Size.Z)
			PartYTop.Position = Vector3.new(Object.Position.X, PartYTop.Position.Y, PartYTop.Position.Z)
			
		end	
		if PartYBottom.Size.X + 0.01 >= Object.Size.X then
			PartYBottom.Size = Vector3.new(Object.Size.X, PartYBottom.Size.Y, PartYBottom.Size.Z)
			PartYBottom.Position = Vector3.new(Object.Position.X, PartYBottom.Position.Y, PartYBottom.Position.Z)
		
		end	
	end
	
	if PartYTop then
		if PartYTop.Size.Y >= Object.Size.Y then
			PartYTop.Size = Vector3.new(PartYTop.Size.X, Object.Size.Y, PartYTop.Size.Z)
			PartYTop.Position = Vector3.new(PartYTop.Position.X, Object.Position.Y, PartYTop.Position.Z)
		end	
		
		if PartYTop.Size.Z + 0.01 >= Object.Size.Z then
			PartYTop.Size = Vector3.new(PartYTop.Size.X, PartYTop.Size.Y, Object.Size.Z)
			PartYTop.Position = Vector3.new(PartYTop.Position.X, PartYTop.Position.Y, Object.Position.Z)
		
		end	
		if PartYBottom.Size.Z + 0.01 >= Object.Size.Z then
			PartYBottom.Size = Vector3.new(PartYBottom.Size.X, PartYBottom.Size.Y, Object.Size.Z)
			PartYBottom.Position = Vector3.new(PartYBottom.Position.X, PartYBottom.Position.Y, Object.Position.Z)
		
		end	
		
	end
	
Model:SetPrimaryPartCFrame(RealObject.CFrame)	
TempObject:Destroy()
TempSubtractor:Destroy()
RealObject:Destroy()


Edit: Fixed all the bugs when you rotate things

Screenshots:

image

image

image

10 Likes

Bump because I edited the topic after

its meant for fast cuts? roblox csg has the benefit of better cutting but this is good for things like bullet holes or really basic things that just need to be fast.

I love this so much, but its hard to use for a practical example in its current state. If you could make this in a modulescript, it would be greatly appreciated!

1 Like

still working on that, took some time to chill because I spent days straight writing this. However I want to optimize cutting for a module to add things like part reusing and “cut start” and “cut end” functions and maybe welding

1 Like

If you want this in module form you can find that here