Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- local behaviour = { }
- behaviour.__index = behaviour
- local plrService = game:GetService("Players")
- local runService = game:GetService("RunService")
- local pfnService = game:GetService("PathfindingService")
- local NPCs, Folder = { }, game.Workspace:WaitForChild("NPCs")
- function behaviour.new(rig)
- local self = setmetatable({ }, behaviour)
- for _, part in (rig:GetDescendants()) do
- if part:IsA("BasePart") then
- part:SetNetworkOwner(nil)
- end
- end
- self.Character = rig
- self.Humanoid = rig.Humanoid
- self.HumanoidRoot = rig.HumanoidRootPart
- self.Target = nil
- self.Path = nil
- self.Goal = nil
- self.Step = nil
- self.IsMoving = false
- self.IsDated = false
- self.Thread = nil
- return self
- end
- function behaviour:getPlayerPath(target, origin)
- local path = pfnService:CreatePath({
- AgentCanJump = true,
- AgentCanClimb = true,
- AgentRadius = 3,
- })
- local goal = target.Character:WaitForChild("HumanoidRootPart")
- local success, error = pcall(function()
- path:ComputeAsync(origin or self.HumanoidRoot.Position, goal.Position)
- end)
- if not success or path.Status ~= Enum.PathStatus.Success then
- return nil
- end
- return path
- end
- function behaviour:getClosestPlayer()
- local target = {name = nil; dist = nil;}
- for index, player in pairs(plrService:GetPlayers()) do
- if player.Character then
- local HRP = player.Character:WaitForChild("HumanoidRootPart")
- local distance = (self.HumanoidRoot.Position - HRP.Position).Magnitude
- if target["dist"] == nil or distance <= target["dist"] then
- target["name"] = player.Name
- target["dist"] = distance
- end
- end
- end
- return target["name"] and plrService:FindFirstChild(target["name"]) or nil
- end
- function behaviour:usePlayerPath()
- self.IsMoving = true
- local waypoints
- if self.Path then
- waypoints = self.Path:GetWaypoints()
- else
- self.Path = self:getPlayerPath(self.Target)
- if not self.Path then
- task.wait()
- self:usePlayerPath()
- return
- end
- waypoints = self.Path:GetWaypoints()
- end
- for i, waypoint in ipairs(waypoints) do
- if i ~= 1 or waypoint.Action == Enum.PathWaypointAction.Jump or self.Humanoid:GetState() == Enum.HumanoidStateType.Climbing then
- self.Step = waypoint.Position
- self.Humanoid:MoveTo(waypoint.Position)
- if waypoint.Action == Enum.PathWaypointAction.Jump then
- self.Humanoid.Jump = true
- end
- local allow = 0
- while (self.HumanoidRoot.Position - waypoint.Position).magnitude > 3.8 and allow < 5 do
- allow = allow + 1
- game:GetService("RunService").Heartbeat:wait()
- end
- if self.IsDated then
- self.IsDated = false
- self:usePlayerPath()
- return
- end
- end
- end
- self.IsMoving = false
- end
- runService.Stepped:Connect(function()
- for index, NPC in ipairs(NPCs) do
- local self = NPC
- self.Target = self:getClosestPlayer()
- if self.Target and self.Target.Character then
- if not self.Goal or (self.Target.Character.HumanoidRootPart.Position - self.Goal).Magnitude > 0.65 then
- self.Goal = self.Target.Character.HumanoidRootPart.Position
- if self.Humanoid:GetState() == Enum.HumanoidStateType.Climbing and self.Humanoid.MoveDirection.Magnitude > 0 then
- if self.Target.Character.Humanoid:GetState() ~= Enum.HumanoidStateType.Climbing then
- return
- end
- end
- if self.IsMoving then
- self.IsDated = true
- self.Path = self:getPlayerPath(self.Target, self.Step)
- return
- end
- self.Path = self:getPlayerPath(self.Target)
- if self.Path then
- self:usePlayerPath()
- end
- end
- else
- self.Humanoid:MoveTo(self.HumanoidRoot.Position)
- end
- end
- end)
- for index, NPC in pairs(Folder:GetChildren()) do
- if NPC:IsA("Model") and NPC:FindFirstChild("Humanoid") then
- local object = behaviour.new(NPC)
- table.insert(NPCs, object)
- end
- end
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement