Help with object interacting with light

Hello! I am fairly new to the Dev Forum so please feel free to let me know if I am posting in the wrong category. :smiley:

So, I am creating a new game and am trying to get a part of the game where you have to aim your flashlight (while it’s on of course) at a monster to make it randomly teleport away into a location (when the monster enters the cone of light produced by a spotlight inside the flashlight model). The script is a local script attached to a handle. The handle also contains the spotlight. The handle is attached to the Flashlight tool. I can’t seem to get the script to work though and would really love some help with it. Currently nothing happens, the chaser doesn’t teleport, and no errors pop up.

local positions = { Vector3.new(10, 0, 0), Vector3.new(20, 0, 0), Vector3.new(30, 0, 0)}
local flashlight = script.Parent.Parent -- the flashlight tool
local handle = flashlight.Handle
local spotlight = handle.SpotLight
local chaser

function spawnChaser()
    local randomPosition = positions[math.random(1, #positions)]
    chaser = game.Workspace:FindFirstChild("Chaser")
    if chaser then
        chaser = chaser:Clone()
        chaser.Parent = game.Workspace
        chaser.PrimaryPart.CFrame = CFrame.new(randomPosition)
    else
        print("Chaser object not found in Workspace")
    end
end

function isChaserInConeOfLight()
    local coneOfLight = spotlight:GetCone()
    local chaser = game.Workspace:FindFirstChild("Chaser")
    if chaser then
        local chaserPosition = chaser.PrimaryPart.Position
        local distance = (chaserPosition - coneOfLight.PointAt).Magnitude
        local halfAngle = math.rad(coneOfLight.OuterAngle / 2)
        local opposite = math.tan(halfAngle) * distance
        local coneRadius = opposite * math.cos(halfAngle)
        local direction = coneOfLight.Direction
        local pointOnCone = coneOfLight.PointAt - (direction * distance)
        local planeNormal = direction:Cross(Vector3.new(0, 1, 0)).Unit
        local pointOnPlane = pointOnCone - (planeNormal * coneRadius)
        local chaserToPlane = pointOnPlane - chaserPosition
        local angle = math.acos(chaserToPlane.Unit:Dot(chaser.PrimaryPart.CFrame.LookVector.Unit))
        return angle <= halfAngle
    end
    return false
end

function onPartTouched(part)
    if part == chaser.PrimaryPart and isChaserInConeOfLight() then
        chaser:Destroy()
        wait(5)
        spawnChaser()
    end
end

function onActivated()
    if spotlight.Parent and spotlight.Parent:FindFirstChild("Touched") then
        spotlight.Parent.Touched:Connect(onPartTouched)
    else
        print("Spotlight or its parent not found")
    end 
    spawnChaser()
end

flashlight.Activated:Connect(onActivated)

Welcome to the DevForum! :smile:

It’s hard to tell from your code, but have you tried implementing a .Touched for a cone object? You could create a cone part that represents the range of the spotlight and use the .Touched event. Cones don’t come pre-built into studio so you will have to create a MeshPart in Blender or find one in the Toolbox under Meshes.

image

If you’ve already implemented that, consider using workspace:GetPartsInPart() instead of conical math. It will return a list of parts intersecting the cone part, if one of the parts returned belongs to the monster you can do your chaser:Destroy().

Hope this helps! :slight_smile:

Thank you! I have started creating this now. :smiley:

1 Like

This topic was automatically closed 14 days after the last reply. New replies are no longer allowed.