So little bit dinging on Module script, I finally did it!
Of course, it’s still can be dodged by jumping around, but it became much harder to dodge from.
Thank you for help and other people to!
If any other people has the same issue as mine with the aim accuracy of a NPC, here is my final script to check how it works using this module script → https://devforum.roblox.com/t/predict-projectile-ballistics-including-gravity-and-motion
My Final Script:
local animator = npc.Humanoid.Animator
local animation = animator.BALLTHROW
local loadAnim = animator:LoadAnimation(animation)
local isAnimPlay = false
local npcHum = npc:WaitForChild("Humanoid")
local CalTrejectory = require(script.CalculateTrajectory)
function EnemyNear()
local nearestPlr = nil
local shortestDistance = 125
for _, plr in pairs(game.Players:GetPlayers()) do
if plr.Character and plr.Character:FindFirstChild("HumanoidRootPart") then
local distance = (npc.HumanoidRootPart.Position - plr.Character.HumanoidRootPart.Position).magnitude
if distance <= shortestDistance then
nearestPlr = plr
shortestDistance = distance
end
end
end
return nearestPlr
end
function throw()
local EnemyPos = EnemyNear()
if EnemyPos then
local StartPos = npc.Torso.BallSpawn.Position
local Root = EnemyPos.Character.HumanoidRootPart
local BallSpeed = 178.00707
local pickLongest = false
local G = workspace.Gravity
local aimAt = CalTrejectory.SolveTrajectory(
StartPos,
BallSpeed,
Root.Position,
Root.AssemblyLinearVelocity,
pickLongest,
G
) or (StartPos + npc.Torso.BallSpawn.CFrame.LookVector * 10)
if aimAt then
local SuperBallclone = game.ServerStorage["BALL!"]:Clone()
--local Force = Thrown / Duration + Vector3.new(0, workspace.Gravity * Duration * 0.5, 0)
SuperBallclone.Parent = workspace
SuperBallclone.Position = StartPos
SuperBallclone:ApplyImpulse((aimAt - StartPos).Unit * BallSpeed * SuperBallclone.AssemblyMass)
SuperBallclone:SetNetworkOwner(nil)
local onceHit = false
SuperBallclone.Touched:Connect(function(hit, hum)
local hitHum = hit.Parent:FindFirstChild("Humanoid")
if hitHum and hitHum ~= npcHum and not onceHit then
hitHum:TakeDamage(11.00707)
onceHit = true
task.wait(1)
onceHit = false
end
end)
end
end
end
while task.wait(math.random(0.1, 2.00707)) do
if EnemyNear() then
loadAnim:Play()
end
wait(0.4700707)
throw()
wait(1)
end
I spend more than 20 days just to research and script to make my NPC throw projectile as accurate as possible. Some laggy players may struggle on this NPC.
Explanation:
First you need to put the Module script on the your main Projectile script and write
local CalTrejectory = require(script.CalculateTrajectory)
in your main projectile script to get Module script work.
Then just create a variable and insert the function from module script like this
local aimAt = CalTrejectory.SolveTrajectory()
SolveTrajectory is the function from module script.
And then, the only thing you need to put inside of this function:
The start position which I wrote first
StartPos,
And then the speed of your projectile, it can be any number by your choice.
BallSpeed
Then the position you want your projectile to go which I put:
Root.Position
→ player’s HumanoidRootPart position
Then the velocity of the target
Root.AssemblyLinearVelocity
Then the pickLongest, I actually do not know what does it do, I just read the module script and saw it’s a boolean, I just write it as false
and then put the gravity which I put as:
G
Which is local G = workspace.Gravity
After these steps, I wrote ApplyImpluse
calculation aim with start pos, multiplying to speed of ball, and it’s mass which is the law from physics, I don’t remember the name
SuperBallclone:ApplyImpulse((aimAt - StartPos).Unit * BallSpeed * SuperBallclone.AssemblyMass)
Now you’re good to go!