I need help with my raycastHitboxV4 npc attacks

Well what I want to do is add the raycashitboxV4 to my npc so that my npc has an attack according to the animations and his hitbox does not have excessive range since I do not want the npc to hit me from behind illogically since when I try the npc it does its function, it attacks but it doesn’t hurt me and it doesn’t play the sounds of damage. The truth is that I don’t receive any damage until the raycast tries to register the accessories and parts of the player but it marks them as an error in the console, Well here I leave the part of my script that contains the connected raycasthibox, it’s not all, but the rest has nothing to do with this. If anyone knows and can help me I would appreciate it. I’m a newbie to raycasting. I have almost no idea how to put it. Some examples would help thanks

local ReplicatedStorage = game:GetService("ReplicatedStorage")
local RaycastHitbox = require(ReplicatedStorage.RaycastHitboxV4)
local Z = script.Parent
local humanoid = Z.Humanoid
local attack1 = Z.Head:FindFirstChild("attack1")
local attack2 = Z.Head:FindFirstChild("attack2")
Z.HumanoidRootPart:SetNetworkOwner(nil)

local newHitbox = RaycastHitbox.new(Z["Right Arm"])
local newHitbox2 = RaycastHitbox.new(Z["Left Arm"])
local Params = RaycastParams.new()
Params.FilterDescendantsInstances = {Z}
Params.FilterType = Enum.RaycastFilterType.Exclude
newHitbox.RaycastParams = Params
newHitbox2.RaycastParams = Params



local function canSeeTarget(target)
	local origin = Z.HumanoidRootPart.Position
	local direction = (target.HumanoidRootPart.Position - Z.HumanoidRootPart.Position).unit * 75
	local ray = Ray.new(origin, direction)

	local hit, pos = workspace:FindPartOnRay(ray, Z)


	if hit then
		if hit:IsDescendantOf(target) then
			return true
		end
	else
		return false
	end
end

local function findTarget()
	local players = game.Players:GetPlayers()
	local maxDistance = 75
	local nearestTarget

	for index, player in pairs(players) do
		if player.Character then
			local target = player.Character
			local distance = (Z.HumanoidRootPart.Position - target.HumanoidRootPart.Position).Magnitude

			if distance < maxDistance and canSeeTarget(target) then
				nearestTarget = target
				maxDistance = distance
			end
		end
	end

	return nearestTarget
end

local function getPath(destination)
	local PathfindingService = game:GetService("PathfindingService")

	local pathParams = {
		["AgentHeight"] = 15,
		["AgentRadius"] = 4,
		["AgentCanJump"] = false
	}

	local path = PathfindingService:CreatePath(pathParams)

	path:ComputeAsync(Z.HumanoidRootPart.Position, destination.Position)

	return path
end

local function attack(target)
	local distance = (Z.HumanoidRootPart.Position - target.HumanoidRootPart.Position).Magnitude

	if distance > 4 then

		humanoid:MoveTo(target.Torso.Position + target.Torso.Velocity)


	else
		local attackAnim = humanoid:LoadAnimation(script.Attack)
		attackAnim:Play()
		wait(0.11)
		newHitbox:HitStart()
		newHitbox2:HitStart()
		humanoid.WalkSpeed = 1
		wait(0.3)
		newHitbox:HitStop()
		newHitbox2:HitStop()
		humanoid.WalkSpeed = 15
	end
end

newHitbox.OnHit:Connect(function(target,hit, humanoid)
	if attack.Parent:FindFirstChildOfClass("Humanoid") then
		attack.target.Humanoid:TakeDamage(10)
	end
	if hit then

		local random = math.random(1, 3)
		if random == 1 then
			attack1:Play()
			local damage1 = script:WaitForChild("damage1"):Clone()
			damage1.Parent = target.Torso
			damage1:Play()
		elseif random == 2 then
			local damage2 = script:WaitForChild("damage2"):Clone()
			damage2.Parent = target.Torso
			damage2:Play()
			attack2:Play()
		elseif random == 3 then
			local damage3 = script:WaitForChild("damage3"):Clone()
			damage3.Parent = target.Torso
			damage3:Play()
		end
	end
end)
newHitbox2.OnHit:Connect(function(target,hit, humanoid)
	if attack.Parent:FindFirstChildOfClass("Humanoid") then
		attack.target.Humanoid:TakeDamage(10)
	end
	if hit then
	
	local random = math.random(1, 3)
	if random == 1 then
		attack1:Play()
		local damage1 = script:WaitForChild("damage1"):Clone()
		damage1.Parent = target.Torso
		damage1:Play()
	elseif random == 2 then
		local damage2 = script:WaitForChild("damage2"):Clone()
		damage2.Parent = target.Torso
		damage2:Play()
		attack2:Play()
	elseif random == 3 then
		local damage3 = script:WaitForChild("damage3"):Clone()
		damage3.Parent = target.Torso
		damage3:Play()
		end
	end
end)

3 Likes

First off, the variable attack is a function. Use target.Parent.Humanoid instead.

Another thing is that the variable name random is already taken by something from roblox. Change it to something else like rand or randomResult


Also both your OnHit functions are the same so you should move it into one function and call them on both hands. Having 2 separate ones makes you have to edit both if you change one.


Also do you have any errors, what are they?

1 Like

im going to try that and yea i got errors in the console like Workspace.NoobZombie.Sys:98 attempt to index function with ´Parent´ the same error but with line 122 Workspace.NoobZombie.Sys:122 attempt to index function with ´Parent´

2 Likes

yeah thats probably because your using the attack function wrong.

this is how you would use your attack function:

attack(target) -- target would be a character

-- this would result in an error
attack.target.Humanoid:TakeDamage()
2 Likes

ohh okay let me try these changes

2 Likes

its this good?

local function OnHit(target, hit, humanoid)
	if attack.Parent:FindFirstChildOfClass("Humanoid") then
		attack.Humanoid:TakeDamage(10)

		if hit then
			local randomResult = math.random(1, 3)
			if randomResult == 1 then
				attack1:Play()
				local damage1 = script:WaitForChild("damage1"):Clone()
				damage1.Parent = target.Torso
				damage1:Play()
			elseif randomResult == 2 then
				local damage2 = script:WaitForChild("damage2"):Clone()
				damage2.Parent = target.Torso
				damage2:Play()
				attack2:Play()
			elseif randomResult == 3 then
				local damage3 = script:WaitForChild("damage3"):Clone()
				damage3.Parent = target.Torso
				damage3:Play()
			end
		end
	end
end

newHitbox.OnHit:Connect(OnHit)
newHitbox2.OnHit:Connect(OnHit)
1 Like

no because attack is still a function. you cant access .Parent from a function

you have to get the humanoid hit by doing:

hit.Parent.Humanoid
1 Like

I did what you said but now I don’t have a problem with the script but now my problem is that the npc won’t do any damage to the player I don’t know if I did something wrong or did i forgot to connect it im confused anyways here is the script part

local function OnHit(target, hit, humanoid)
	if hit:FindFirstChildOfClass("Humanoid") then
		hit.Parent.Humanoid:TakeDamage(10)
			local randomResult = math.random(1, 3)
			if randomResult == 1 then
				local damage1 = script:WaitForChild("damage1"):Clone()
				damage1.Parent = target.Torso
				damage1:Play()
			elseif randomResult == 2 then
				local damage2 = script:WaitForChild("damage2"):Clone()
				damage2.Parent = target.Torso
				damage2:Play()
			elseif randomResult == 3 then
				local damage3 = script:WaitForChild("damage3"):Clone()
				damage3.Parent = target.Torso
				damage3:Play()
			end
		end
	end
1 Like

hit is the part being hit, it doesnt have a humanoid in it.

hit is parented inside the character so you will need to use hit.Parent.

Example

hit.Parent:FindFirstChildofClass("Humanoid")

everything else looks fine after that it should work unless you have other issues in your code.

Yes, it works very well, I don’t have problems in the console anymore, my only problem is that the raycast doesn’t do any damage. In fact, since I had this error, it could never do any damage, I don’t know, but I have a question and that is that I shouldn’t connect the OnHit function. somewhere? Since seeing my script well and it happened to me but there is a part of the script that takes the function that you had told me previously the attack (target) here its the part that i mean

			local target = findTarget()
			if target and target.Humanoid.Health > 0 then
				print("PLAYER FOUND", target.Name)
				humanoid.WalkSpeed = 12.6

				attack(target)
				break
			else
				humanoid.WalkSpeed = 12.6
				print("Moving to ", waypoint.Position)
				local waypointPosition = waypoint.Position
				humanoid:MoveTo(waypointPosition)
				repeat

u won’t do any damage if the OnHit function isn’t connected to a hit event.