So I've been spending a bit of time trying to make some bullets to work for the guns used in a game I'm helping out with... After some issues Cframe's not being the greatest, and with Tween making it smoother (not actually implemented as of yet as I haven't worked with the service) but not fixing the issue I was looking to explore other options. It's fairly common knowledge that 2 anchored objects cannot touch. The issue is, both objects have to be anchored, as one is walls, and if the bullets are not anchored, they go under the effect of gravity far too quick. So a simple solution I have thought of is applying a body force to negate gravity. However when shooting at angles up or down, I'm not sure how realistic this is.
That became an option due to the issues I had with using :GetTouchingParts(), as the bullets start by touching the gun's handle, and then may make contact with each other as there is a gun with a multi-shot spray, and I've not really seen a good way to filter out certain touching parts.
The other option there is, is using FastCast. From reading the site and looking at the module scripts it seems really great, however being fairly new to scripting, is incredibly overwhelming and I have absolutely no idea where to start.
What I'd like to know is whether the bodyforce to negate gravity is actually feasible, and by combining that with tweening will work well enough (the max server size is only 6 players so it won't be overwhelmed with bullets), or whether changing to fast cast is really the only way forwards. And if that is the case, any pointers on how to implement it would be extremely helpful.
Here is the code for when the gun is fired and a bullet is created (which deals with getting the bullet data for that gun and also directing the offset for the spray of the bullets:
local GunData = require(game.ReplicatedStorage.GunData)
local rep = 1
game.ReplicatedStorage.ShootGun.OnServerEvent:Connect(function(Player, TargetLocation, Handle)
if Player.Character == nil then
return
end
if Handle then
local Tool = Handle.Parent
if Tool:IsA("Tool")then
if Tool.Parent == Player.Character then
local relevantData = GunData[Tool.Name]
if relevantData ~= nil then
for count = 1,relevantData.REP do
Handle.Sound:Play()
local Beam = Instance.new("Part", workspace)
Beam.Color = relevantData.COLOR
Beam.FormFactor = "Custom"
Beam.Transparency = 0.25
Beam.Material = "Neon"
Beam.Anchored = true
Beam.CanCollide = false
Beam.Name = "Bullet"
Beam:SetAttribute("Speed",relevantData.SPEED)
Beam:SetAttribute("Damage",relevantData.DMG)
Beam.CanTouch = true
Beam:SetAttribute("Shooter",Tool.Parent.Name)
local Distance = (TargetLocation - Handle.Position).magnitude
if Distance >= relevantData.RANGE then
Distance = relevantData.RANGE
end
local NewAngle = CFrame.Angles(math.rad(math.random(-relevantData.ANGLE,relevantData.ANGLE)),math.rad(math.random(-relevantData.ANGLE,relevantData.ANGLE)),math.rad(math.random(-relevantData.ANGLE,relevantData.ANGLE)))
Beam.Size = Vector3.new(relevantData.WIDTH, relevantData.WIDTH, Distance)
Beam.CFrame = CFrame.new(Handle.Position, TargetLocation) * CFrame.new(0, 0, -Distance/2)
local offset = Handle.CFrame:Inverse()*Beam.CFrame
local handleStartCFrame = Handle.CFrame
local newCFrame = handleStartCFrame*NewAngle
Beam.CFrame = newCFrame*offset
local moveBullets = script.bulletMovement:Clone()
moveBullets.Parent = Beam
local hitBullets = script.hitDetection:Clone()
hitBullets.Parent = Beam
Beam.Parent = game.Workspace["Futuristic Tycoon"].Bullets
if relevantData.DELAY ~= 0 then
wait(relevantData.DELAY)
end
end
end
end
end
end
end)
Here's the movement script:
scrpar = script.Parent
speed = scrpar:GetAttribute("Speed")
while true do
if scrpar.Name == "Bullet" then
wait()
for count = 1,20 do
scrpar.CFrame = scrpar.CFrame + scrpar.CFrame.lookVector * speed
wait()
end
scrpar:Destroy()
end
end
Finally, the hit detection... only detects humanoids for now as they are not anchored:
local Players = game:GetService("Players")
local scrpar = script.Parent
local damage = scrpar:GetAttribute("Damage")
local shooter = scrpar:GetAttribute("Shooter")
scrpar.Touched:Connect(function(hit)
print("touched")
local humanoid = hit.Parent:FindFirstChild("Humanoid") or hit.Parent.Parent:FindFirstChild("Humanoid")
if humanoid then
local player = Players:GetPlayerFromCharacter(humanoid.Parent).Name
if player ~= shooter then
humanoid.Health -= damage
scrpar:Destroy()
end
end
end)

1 comment
You can use a BodyForce object and simulate gravity yourself. That is what I commonly do. If you want to see what I am talking about, send me a message (with context) on Discord (phxntxsmic#2021)