At the moment I’m just making bullet physics cause I’m bored, I’ve decided I want it to be super optimized so I can have tens of thousands of bullets alive at once, however an issue I’m having is where the trails are coming from just below the part then going up to where they should be (which makes no sense)
(I call Render.new() then I set the position of all the attachments to where they should be so I have no clue why its doing this)
Bullet Module:
local look = CFrame.lookAt
local module = {}
module.__index = module
function module.new(origin,direction,initialVelocity,gravity,drag,mass,start)
local self = setmetatable({},module)
self.Position = origin
self.Direction = direction
self.Velocity = initialVelocity
self.Gravity = gravity
self.Drag = drag
self.Mass = mass
self.Born = start
return self
end
function module:step(dt)
self.Position += self.Velocity * dt
self.Velocity += (self.Gravity * self.Mass) * dt
self.Direction = look(self.Position,self.Position+(self.Velocity.Unit)).LookVector
self.Velocity += -(self.Direction * self.Drag)
end
function module:Destroy()
setmetatable(self,nil)
self = nil
end
return module
Bullet Render:
local module = {}
module.__index = module
function module.new(RenderPart,Bullet,AutoApply)
local self = setmetatable({},module)
self.Attachment = Instance.new("Attachment")
self.Connection1 = Instance.new("Attachment")
self.Connection2 = Instance.new("Attachment")
self.Connection1Offset = RenderPart.Connection1.CFrame
self.Connection2Offset = RenderPart.Connection2.CFrame
self.Trail = RenderPart.Trail:Clone()
self.Trail.Enabled = false
self.Trail.Attachment0 = self.Connection1
self.Trail.Attachment1 = self.Connection2
self.Bullet = Bullet
self:Render()
return self
end
function module:ApplyParent(Part : instance)
self.Attachment.Parent = Part
self.Connection1.Parent = Part
self.Connection2.Parent = Part
self.Trail.Parent = Part
end
function module:ClearTrail()
self.Trail:Clear()
end
function module:Render(CustomPosition : Vector3?)
self.Attachment.WorldPosition = CustomPosition or self.Bullet.Position
self.Connection1.WorldCFrame = self.Attachment.WorldCFrame * self.Connection1Offset
self.Connection2.WorldCFrame = self.Attachment.WorldCFrame * self.Connection2Offset
self.Trail.Enabled = true
end
function module:Destroy()
setmetatable(self,nil)
self.Attachment:Destroy()
self.Connection1:Destroy()
self.Connection2:Destroy()
self.Trail:Destroy()
self = nil
end
return module
Main Script (Don’t mind the messy code it’s just for testing):
local bulletModule = require(script.Parent.Bullet)
local bulletrender = require(script.Parent.BulletRender)
local renderPart = script.Parent.BulletRenderPart
local mainpart = workspace.Baseplate
local bullets = {}
local rs = game:GetService("RunService")
rs.Stepped:Connect(function(_,dt)
for I,v in bullets do
v.bullet:step(dt)
v.render:Render()
if tick()-v.bullet.Born > 5 then
v.bullet:Destroy()
v.render:Destroy()
table.remove(bullets,I)
end
end
end)
local bulletSpeed = 800
local bulletMass = 14.5 -- grams
for i = 1,5000 do
local r = Random.new()
local dir = workspace.ORIGIN.CFrame.LookVector
local origin = workspace.ORIGIN.Position
local BULLET = bulletModule.new(origin,dir,dir*bulletSpeed,Vector3.new(0,-9.6,0),.1,bulletMass,tick()) -- makes the bullet
local r = bulletrender.new(renderPart,BULLET,true) -- bullet renderer
r:ClearTrail()
r:ApplyParent(mainpart)
table.insert(bullets,{bullet = BULLET,render = r})
print(("active bullets: %s"):format(#bullets))
task.wait(.01)
end
If you have any more questions about the code feel free to ask