EN
Key Required

EN

[FPS] Enforcementzylczylc 138 views 533 executesUpdated Aug 21, 2026
Unrated
00
Lua Script•1487 lines (52911 chars)
-- ===============================
-- SCRIPT START
-- ===============================

local Debris = workspace.Debris
local RunService = game:GetService("RunService")
local ReplicatedStorage = game:GetService("ReplicatedStorage")
local Modules = ReplicatedStorage:FindFirstChild("Modules")
local Weapons = ReplicatedStorage:FindFirstChild("Weapons")
local Camera = workspace.CurrentCamera
local Players = game:GetService("Players")
local localPlayer = Players.LocalPlayer
local mouse = localPlayer:GetMouse()

-- ===============================
-- Circle Drawing
-- ===============================
local aimbotCircle = Drawing.new("Circle")
aimbotCircle.Visible = false

local circleConnection = nil

-- ===============================
-- Weapon / Frag Functions (unchanged)
-- ===============================
function getWeapons()
    local child = {}
    for _, wpn in ipairs(Weapons:GetChildren()) do 
        if wpn:IsA("Folder") then
            table.insert(child, wpn)
        end
    end
    return child
end

function getFrags()
    local child = {}
    for _, nades in ipairs(Debris:GetChildren()) do
        local grenades = getWeapons()
        for _, x in grenades do
            if nades.Name == x.Name or nades.Name then
                table.insert(child, nades)
            end
        end
    end
    return child
end

local weapons = getWeapons()

-- ===============================
-- Library / UI
-- ===============================
local Library = loadfile("nl.luau")()
local Indicator = Library:CreateIndicator();
local Notification = Library:CreateNotification();
local Logging = Library:CreateLogger();

local Window = Library:CreateWindow({
    Logo = Library.GlobalLogo,
    Name = "Enforcement",
    Content = "EN",
    Size = Library.Scales.Default,
    ConfigFolder = "LibraryConfigs",
    Enable3DRenderer = false,
    Keybind = "Insert"
});
local Watermark = Window:Watermark()
local ping = Watermark:AddBlock("chart-four-vertical-bars" , "0MS");
local id = Watermark:AddBlock("house", game.PlaceId);
local user = Watermark:AddBlock("circle-person", localPlayer.DisplayName)

local UITogg = Watermark:AddBlock("circle-minus" , "Neverlose");

UITogg:Input(function()
	Window:ToggleInterface();
end);

local Tab = Window:AddTab({
    Icon = "Eye",
    Name = "Rage"
})

local MainSection = Tab:AddSection({
    Name = "Main"
})
local Visual = Tab:AddSection({
    Name = "Visual",
    Position = "left"
})
local Modification = Tab:AddSection({
    Name = "Mods",
    Position = "right"
})

local EnabledLabel = MainSection:AddLabel("Enabled")
local SilentLabel = MainSection:AddLabel("Silent Aim")
local WallbangLabel = MainSection:AddLabel("Visible Check")

local EspEnabledLabel = Visual:AddLabel("Enabled")
local TeamCheckLabel = Visual:AddLabel("TeamCheck")
local OutlinesLabel = Visual:AddLabel("Outlines")
local ChamsLabel = Visual:AddLabel("Chams")
local ShowWeaponName = Visual:AddLabel("Gun")
local ShowHealth = Visual:AddLabel("Health")
local ShowDistance = Visual:AddLabel("Distance")
local ShowNames = Visual:AddLabel("Names")

local RecoilLabel = Modification:AddLabel("Recoil")
local SpreadLabel = Modification:AddLabel("Spread")
local FireRateLabel = Modification:AddLabel("FireRate")
local AmmoLabel = Modification:AddLabel("Ammo")
local TimesLabel = Modification:AddLabel("Times")
local PenetrationLabel = Modification:AddLabel("Penetration")
local AutomaticLabel =  Modification:AddLabel("Automatic")
local WeaponSpeedLabel = Modification:AddLabel("WeaponSpeed")
local BulletsLabel = Modification:AddLabel("Bullets")
local BlastRadiusLabel = Modification:AddLabel("BlastRadius")
local ProjectileSpeedLabel = Modification:AddLabel("ProjectileSpeed")

BulletsLabel:ToolTip("bullet per round")

local Notify = MainSection:AddLabel("Notifications")
Notify:ToolTip("Notify, Incoming Frags, Semtex, ESP")

-- Existing toggles
local Enabled_RAGE = EnabledLabel:AddToggle({
    Default = false,
    Callback = function(state)
        return state
    end,
    Flag = "wpn_enabled"
})

-- Silent Aim Toggle
local SilentToggle = SilentLabel:AddToggle({
    Default = false,
    Callback = function(state)
        print("Aimbot toggled:", state)
        if state then
            aimbotCircle.Visible = true
            if not circleConnection then
                circleConnection = RunService.RenderStepped:Connect(function()
                    local x = mouse.X
                    local y = mouse.Y
                    aimbotCircle.Position = Vector2.new(x, y + 60)
                    aimbotCircle.Visible = true
                end)
            end
        else
            if circleConnection then
                circleConnection:Disconnect()
                circleConnection = nil
                aimbotCircle.Visible = false
            end
        end
        return state
    end,
    Flag = "silent_enabled"
})
local SilentOption = SilentLabel:AddOption()
local radius_aim = SilentOption:AddLabel("Radius"):AddSlider({
    Default = 50,
    Min = 0,
    Max = 1000,
    Type = "",
    Rounding = 0,
    Flag = "MySlider",
    Size = 125,
    Callback = function(value)
        aimbotCircle.Radius = value
    end,
})
local color_aim = SilentOption:AddLabel("Color"):AddColorPicker({
    Default = Color3.fromRGB(255, 255, 255),
    Flag = "MyColor",
    Callback  = function(state)
        aimbotCircle.Color = state
    end,
})
local numsides_aim = SilentOption:AddLabel("sides"):AddSlider({
    Default = 0,
    Min = 0,
    Max = 12,
    Type = "",
    Rounding = 0,
    Flag = "MySlider",
    Size = 125,
    Callback = function(value)
        aimbotCircle.NumSides = value
    end,
})
local filled_aim = SilentOption:AddLabel("Filled"):AddToggle({
    Default = false,
    Flag = "filled_color",
    Callback  = function(state)
        aimbotCircle.Filled = state
    end,
})
local transparency_aim = SilentOption:AddLabel("Trans"):AddSlider({
    Default = 0,
    Min = 0,
    Max = 1,
    Type = "",
    Rounding = 1,
    Flag = "MySlider",
    Size = 125,
    Callback = function(value)
        aimbotCircle.Transparency = value
    end,
})
WallbangLabel:ToolTip("")
-- Wallbang Toggle
local WallbangToggle = WallbangLabel:AddToggle({
    Default = false,
    Callback = function(state)
        print("Wallbang:", state)
        return state
    end,
    Flag = "wallbang_enabled"
})

-- ===============================
-- INTEGRATED ESP (your source code)
-- ===============================
local runService = game:GetService('RunService')
local coregui = game:GetService('CoreGui')
local players = game:GetService('Players')
local localPlayer = players.LocalPlayer
local camera = workspace.CurrentCamera

local esp = {
    -- settings
    enabled = false,
    teamcheck = true,
    visiblecheck = false,
    outlines = true,
    limitdistance = false,
    shortnames = false,

    maxchar = 4,
    maxdistance = 1200,
    fadefactor = 20,
    arrowradius = 500,
    arrowsize = 20,
    arrowinfo = false,

    -- instances
    --\ @teammates
    team_chams = { false, Color3.new(1, 1, 1), Color3.new(1, 1, 1), .25, .75, true },
    team_boxes = { false, Color3.new(), Color3.new(), 0.95 },
    team_healthbar = { false, Color3.new(), Color3.new() },
    team_kevlarbar = { false, Color3.new(), Color3.new() },
    team_arrow = { false, Color3.new(), 0.5 },
    team_names = { false, Color3.new()},
    team_weapon = { false, Color3.new()},
    team_distance = false,
    team_health = false,

    --\ @enemies
    enemy_chams = { false, Color3.new(1, 1, 1), Color3.new(1, 1, 1), .25, .75, true },
    enemy_boxes = { false, Color3.new(), Color3.new(), 0.95 },
    enemy_healthbar = { false, Color3.new(), Color3.new() },
    enemy_kevlarbar = { false, Color3.new(), Color3.new() },
    enemy_arrow = { false, Color3.new(), 0.5 },
    enemy_names = { false, Color3.new()},
    enemy_weapon = { false, Color3.new()},
    enemy_distance = false,
    enemy_health = false,

    --\ @priority
    priority_chams = { false, Color3.new(1, 1, 1), Color3.new(1, 1, 1), .25, .75, true },
    priority_boxes = { false, Color3.new(), Color3.new(), 0.95 },
    priority_healthbar = { false, Color3.new(), Color3.new() },
    priority_kevlarbar = { false, Color3.new(), Color3.new() },
    priority_arrow = { false, Color3.new(), 0.5 },
    priority_names = { false, Color3.new()},
    priority_weapon = { false, Color3.new()},
    priority_distance = false,
    priority_health = false,

    font = 'Plex',
    textsize = 13,

    -- tables
    players = {},
    priority_players = {},
    connections = {},
    visiblecheckparams = {}
}

-- index optimisations (from your source)
local NEWCF     = CFrame.new
local NEWVEC2   = Vector2.new
local NEWCOLOR3 = Color3.new

local MIN       = math.min
local MAX       = math.max
local ATAN2     = math.atan2
local CLAMP     = math.clamp
local FLOOR     = math.floor
local SIN       = math.sin
local COS       = math.cos
local RAD       = math.rad

local LEN       = string.len
local LOWER     = string.lower
local SUB       = string.sub

local TINSERT   = table.insert
local TFIND     = table.find

-- functions (copied exactly from your source)
function esp:draw(a, b)
    local instance = Drawing.new(a)
    if type(b) == 'table' then
        for property, value in next, b do
            instance[property] = value
        end
    end
    return instance
end
function esp:create(a, b)
    local instance = Instance.new(a)
    if type(b) == 'table' then
        for property, value in next, b do
            instance[property] = value
        end
    end
    return instance
end
local folder = esp:create('Folder', { Parent = coregui })
function esp:setproperties(a, b)
    for i, v in next, b do
        a[i] = v;
    end
    return a
end
function esp:raycast(a, b, c)
    c = type(c) == 'table' and c or {}
    local params = RaycastParams.new();
    params.IgnoreWater = true;
    params.FilterType = Enum.RaycastFilterType.Blacklist;
    params.FilterDescendantsInstances = c;

    local ray = workspace:Raycast(a, b, params);
    if ray ~= nil then
        if ray.Instance.Transparency >= .250 then
            TINSERT(c, ray.Instance);
            local newray = self:raycast(a,b,c)
            if newray ~= nil then
                ray = newray
            end
        end
    end
    return ray
end

function esp.getcharacter(plr)
    return plr.Character
end

function esp.checkalive(plr)
    if not plr then plr = localPlayer end
    local pass = false
    if (plr.Character and plr.Character:FindFirstChild('Humanoid') and plr.Character:FindFirstChild('Head') and plr.Character:FindFirstChild('LeftUpperArm') and plr.Character.Humanoid.Health > 0 and plr.Character.LeftUpperArm.Transparency == 0) then
        pass = true
    end
    return pass
end

function esp.checkteam(plr, bool)
    if not plr then 
        return plr
    end
    return plr ~= localPlayer and bool or localPlayer:GetAttribute("Team") ~= plr:GetAttribute("Team")
end

function esp:checkvisible(instance, origin, params)
    if not params then params = {} end
    local hit = self:raycast(camera.CFrame.p, (origin.Position - camera.CFrame.p).unit * 500, { unpack(params), camera, localPlayer.Character })
    return (hit and hit.Instance:IsDescendantOf(instance)) and true or false
end

function esp:check(plr)
	if plr == players.LocalPlayer then return false; end;
	local pass = true;
	local character = self.getcharacter(plr);
	if not self.checkalive(plr) then
		pass = false;
	elseif esp.limitdistance and (character.PrimaryPart.CFrame.p - workspace.CurrentCamera.CFrame.p).magnitude > esp.maxdistance then
		pass = false;
	elseif esp.teamcheck and not self.checkteam(plr, false) then
		pass = false;
    elseif esp.visiblecheck and not self:checkvisible(character, character.Head, esp.visiblecheckparams) then
        pass = false
	end;
	return pass;
end;

function esp:returnoffsets(x, y, minY, z)
    return {
        NEWCF(x, y, z),
        NEWCF(-x, y, z),
        NEWCF(x, y, -z),
        NEWCF(-x, y, -z),
        NEWCF(x, -minY, z),
        NEWCF(-x, -minY, z),
        NEWCF(x, -minY, -z),
        NEWCF(-x, -minY, -z)
    };
end;

function esp:returntriangleoffsets(triangle)
    local minX = MIN(triangle.PointA.X, triangle.PointB.X, triangle.PointC.X)
    local minY = MIN(triangle.PointA.Y, triangle.PointB.Y, triangle.PointC.Y)
    local maxX = MAX(triangle.PointA.X, triangle.PointB.X, triangle.PointC.X)
    local maxY = MAX(triangle.PointA.Y, triangle.PointB.Y, triangle.PointC.Y)
    return minX, minY, maxX, maxY
end

function esp:convertnumrange(val, oldmin, oldmax, newmin, newmax)
    return (val - oldmin) * (newmax - newmin) / (oldmax - oldmin) + newmin;
end;

function esp:fadeviadistance(data)
    return data.limit and 1 - CLAMP(self:convertnumrange(FLOOR(((data.cframe.p - camera.CFrame.p)).magnitude), (data.maxdistance - data.factor), data.maxdistance, 0, 1), 0, 1) or 1;
end;

function esp:floorvector(vector)
    return NEWVEC2(FLOOR(vector.X),FLOOR(vector.Y))
end
function esp:rotatevector2(v2, r)
	local c = COS(r);
	local s = SIN(r);
	return NEWVEC2(c * v2.X - s * v2.Y, s * v2.X + c * v2.Y);
end;

function esp:add(plr)
    if plr == localPlayer then return end
    local objs = {
        box_fill = esp:draw('Square', { Filled = true, Thickness = 1 }),
        box_outline = esp:draw('Square', { Filled = false, Thickness = 1 }),
        box = esp:draw('Square', { Filled = false, Thickness = 1, Color = NEWCOLOR3(1,1,1) }),
        arrow_name_outline = esp:draw('Text', { Color = NEWCOLOR3(), Font = 2, Size = 13 }),
        arrow_name = esp:draw('Text', { Color = NEWCOLOR3(1,1,1), Font = 2, Size = 13 }),
        arrow_bar_outline = esp:draw('Square', { Filled = true, Thickness = 1 }),
        arrow_bar_inline = esp:draw('Square', { Filled = true, Thickness = 1, Color = NEWCOLOR3(0.3, 0.3, 0.3) }),
        arrow_bar = esp:draw('Square', { Filled = true, Thickness = 1, Color = NEWCOLOR3(1,1,1) }),
        arrow_kevlarbar_outline = esp:draw('Square', { Filled = true, Thickness = 1 }),
        arrow_kevlarbar_inline = esp:draw('Square', { Filled = true, Thickness = 1, Color = NEWCOLOR3(0.3, 0.3, 0.3) }),
        arrow_kevlarbar = esp:draw('Square', { Filled = true, Thickness = 1, Color = NEWCOLOR3(1,1,1) }),
        arrow = esp:draw('Triangle', { Filled = true, Thickness = 1, });
        -- bars
        bar_outline = esp:draw('Square', { Filled = true, Thickness = 1 }),
        bar_inline = esp:draw('Square', { Filled = true, Thickness = 1, Color = NEWCOLOR3(0.3, 0.3, 0.3) }),
        bar = esp:draw('Square', { Filled = true, Thickness = 1, Color = NEWCOLOR3(1,1,1) }),
        kevlarbar_outline = esp:draw('Square', { Filled = true, Thickness = 1 }),
        kevlarbar_inline = esp:draw('Square', { Filled = true, Thickness = 1, Color = NEWCOLOR3(0.3, 0.3, 0.3) }),
        kevlarbar = esp:draw('Square', { Filled = true, Thickness = 1, Color = NEWCOLOR3(1,1,1) }),
        -- text
        name_outline = esp:draw('Text', { Color = NEWCOLOR3(), Font = 2, Size = 13 }),
        name = esp:draw('Text', { Color = NEWCOLOR3(1,1,1), Font = 2, Size = 13 }),
        distance_outline = esp:draw('Text', { Color = NEWCOLOR3(), Font = 2, Size = 13 }),
        distance = esp:draw('Text', { Color = NEWCOLOR3(1,1,1), Font = 2, Size = 13 }),
        weapon_outline = esp:draw('Text', { Color = NEWCOLOR3(), Font = 2, Size = 13 }),
        weapon = esp:draw('Text', { Color = NEWCOLOR3(1,1,1), Font = 2, Size = 13 }),
        health = esp:draw('Text', { Color = NEWCOLOR3(1,1,1), Font = 2, Size = 13, Center = true })
    }
    local chams = { ins = esp:create('Highlight', { Name = plr.Name }) }
    function chams:Remove() chams.ins:Destroy() end
    objs['chams'] = chams
    self.players[plr.Name] = objs
end
function esp:disable(plr)
    local objects = self.players[plr.Name];
    if objects then
        for i, v in next, objects do
            if i == 'chams' then
                v.ins.Enabled = false
            else
                v.Visible = false
            end
        end;
    end;
end;
function esp:remove(plr)
    local objects = self.players[plr.Name];
    if objects then
        for i, v in next, objects do
            v:Remove()
        end;
    end;
    self.players[plr.Name] = nil;
end;

function esp:connect(a, callback)
    local c = a:Connect(callback)
    TINSERT(self.connections, c)
    return c
end

function esp:bindtorenderstep(name, priority, callback)
    local a = {}
    function a:Disconnect()
        runService:UnbindFromRenderStep(name)
    end
    runService:BindToRenderStep(name, priority, callback)
    TINSERT(self.connections, a)
    return a
end

function esp:clearconnections()
    for _, c in next, self.connections do
        c:Disconnect()
    end
end

function esp:update()
    for plr, drawing in next, esp.players do
        local player = players:FindFirstChild(plr)
        if not player then esp.players[plr] = nil continue end
        if esp.enabled and esp.checkalive(player) then
            local character = esp.getcharacter(player)
            local playerName = LEN(plr) > esp.maxchar and esp.shortnames and SUB(plr, 0, esp.maxchar) .. '..' or plr
            local pass = esp:check(player)
            local distance = tostring(FLOOR((character.PrimaryPart.CFrame.p - camera.CFrame.p).Magnitude  / 3))  .. 'm'
            local _, onScreen = camera:WorldToViewportPoint(character['HumanoidRootPart'].Position)
            local centerMassPos = character['HumanoidRootPart'].CFrame
            local transparency = esp:fadeviadistance({
                limit = esp.limitdistance,
                cframe = centerMassPos,
                maxdistance = esp.maxdistance,
                factor = esp.fadefactor
            })
            local kevlar = 0
            if player:FindFirstChild('Kevlar') then
                kevlar = player.Kevlar.Value
            end
            local health = FLOOR(character.Humanoid.Health)

            local flag = 'team_'
            if esp.checkteam(player, false) then
                flag = 'enemy_'
            end

            if TFIND(esp.priority_players, player) then
                flag = 'priority_'
            end

            if not (pass and onScreen) then
                esp:disable(player)
            end

            -- arrows (unchanged)
            drawing.arrow.Visible = esp[ flag .. 'arrow'][1] and pass;
            if drawing.arrow.Visible then
                local proj = camera.CFrame:PointToObjectSpace(centerMassPos.p);
                local ang = ATAN2(proj.Z, proj.X);
                local dir = NEWVEC2(COS(ang), SIN(ang));
                local a = (dir * esp.arrowradius * .5) + camera.ViewportSize / 2;
                local b, c = a - esp:rotatevector2(dir, RAD(30)) * esp.arrowsize, a - esp:rotatevector2(dir, (-RAD(30))) * esp.arrowsize;
                drawing.arrow.PointA = a;
                drawing.arrow.PointB = b;
                drawing.arrow.PointC = c;
                drawing.arrow.Color = esp[ flag .. 'arrow'][2];
                drawing.arrow.Transparency = not onScreen and esp[ flag .. 'arrow'][3] or 0;
                if esp.arrowinfo then
                    local smallestX, smallestY, biggestX, biggestY = esp:returntriangleoffsets(drawing.arrow)
                    -- healthbar, kevlarbar, name (unchanged)
                    drawing.arrow_bar.Visible = not onScreen and drawing.arrow.Visible and esp[ flag .. 'healthbar'][1]
                    drawing.arrow_bar_inline.Visible = drawing.arrow_bar.Visible
                    drawing.arrow_bar_outline.Visible = esp.outlines and drawing.arrow_bar.Visible
                    if drawing.arrow_bar.Visible then
                        drawing.arrow_bar.Color = esp[ flag .. 'healthbar'][3]:Lerp(esp[ flag .. 'healthbar'][2], health / 100)
                        drawing.arrow_bar.Size = esp:floorvector(NEWVEC2(1, ( - health / 100 * ( biggestY - smallestY + 2)) + 3))
                        drawing.arrow_bar.Position = esp:floorvector(NEWVEC2(smallestX - 3, smallestY + drawing.arrow_bar_outline.Size.Y))
                        drawing.arrow_bar.Transparency = transparency
                        drawing.arrow_bar_inline.Size = esp:floorvector(NEWVEC2(1, ( - 1 * ( biggestY - smallestY + 2)) + 3))
                        drawing.arrow_bar_inline.Position = drawing.arrow_bar.Position
                        drawing.arrow_bar_inline.Transparency = transparency
                        drawing.arrow_bar_outline.Size = esp:floorvector(NEWVEC2(1, biggestY - smallestY))
                        drawing.arrow_bar_outline.Position = esp:floorvector(NEWVEC2(smallestX - 2, smallestY + 1))
                        drawing.arrow_bar_outline.Transparency = transparency
                    end

                    drawing.arrow_kevlarbar.Visible = not onScreen and drawing.arrow.Visible and esp[ flag .. 'kevlarbar'][1]
                    drawing.arrow_kevlarbar_inline.Visible = drawing.arrow_kevlarbar.Visible
                    drawing.arrow_kevlarbar_outline.Visible = esp.outlines and drawing.arrow_kevlarbar.Visible
                    if drawing.arrow_kevlarbar.Visible then
                        drawing.arrow_kevlarbar.Color = esp[ flag .. 'kevlarbar'][3]:Lerp(esp[ flag .. 'kevlarbar'][2], kevlar / 100)
                        drawing.arrow_kevlarbar.Size = esp:floorvector(NEWVEC2(( kevlar / 100 * ( biggestX - smallestX)), 1))
                        drawing.arrow_kevlarbar.Position = esp:floorvector(NEWVEC2(smallestX, biggestY + 2))
                        drawing.arrow_kevlarbar.Transparency = transparency
                        drawing.arrow_kevlarbar_inline.Size = esp:floorvector(NEWVEC2((biggestX - smallestX), 1))
                        drawing.arrow_kevlarbar_inline.Position = drawing.arrow_kevlarbar.Position
                        drawing.arrow_kevlarbar_inline.Transparency = transparency
                        drawing.arrow_kevlarbar_outline.Size = drawing.arrow_kevlarbar_inline.Size
                        drawing.arrow_kevlarbar_outline.Position = esp:floorvector(NEWVEC2(smallestX + 1, biggestY + 3))
                        drawing.arrow_kevlarbar_outline.Transparency = transparency
                    end

                    drawing.arrow_name.Visible = not onScreen and drawing.arrow.Visible and esp[ flag .. 'names'][1]
                    drawing.arrow_name_outline.Visible = esp.outlines and drawing.arrow_name.Visible
                    if drawing.arrow_name.Visible then
                        drawing.arrow_name.Text = esp[ flag .. 'distance'] and '['..distance..'] '.. playerName or playerName
                        drawing.arrow_name.Font = Drawing.Fonts[esp.font]
                        drawing.arrow_name.Size = esp.textsize
                        drawing.arrow_name.Color = esp[ flag .. 'names'][2]
                        drawing.arrow_name.Position = esp:floorvector(NEWVEC2(smallestX + (biggestX - smallestX) / 2 - (drawing.arrow_name.TextBounds.X / 2), smallestY - drawing.arrow_name.TextBounds.Y - 2))
                        drawing.arrow_name.Transparency = transparency
                        drawing.arrow_name_outline.Text = drawing.arrow_name.Text
                        drawing.arrow_name_outline.Font = drawing.arrow_name.Font
                        drawing.arrow_name_outline.Size = drawing.arrow_name.Size
                        drawing.arrow_name_outline.Position = drawing.arrow_name.Position + NEWVEC2(1,1)
                        drawing.arrow_name_outline.Transparency = transparency
                    end
                end
            end;

            -- chams
            drawing.chams.ins.Enabled = esp[ flag .. 'chams'][1] and pass
            drawing.chams.ins.Adornee = esp[ flag .. 'chams'][1] and player.Character or nil
            drawing.chams.ins.Parent = folder
            if drawing.chams.ins.Enabled then
                drawing.chams.ins.FillColor = esp[ flag .. 'chams'][2]
                drawing.chams.ins.OutlineColor = esp[ flag .. 'chams'][3]
                drawing.chams.ins.FillTransparency = esp[ flag .. 'chams'][4]
                drawing.chams.ins.OutlineTransparency = esp[ flag .. 'chams'][5]
                drawing.chams.ins.DepthMode = esp[ flag .. 'chams'][6] and Enum.HighlightDepthMode.AlwaysOnTop or Enum.HighlightDepthMode.Occluded
            end;

            if not pass or (not onScreen) then
                continue
            end

            local smallestX, biggestX = math.huge, -math.huge
            local smallestY, biggestY = math.huge, -math.huge

            local y = (centerMassPos.p - character['Head'].Position).magnitude + character['Head'].Size.Y / 2
            local x1 = (centerMassPos.p - character['RightHand'].Position).magnitude
            local x2 = (centerMassPos.p - character['LeftHand'].Position).magnitude
            local minY1 = (centerMassPos.p - character['RightFoot'].Position).magnitude
            local minY2 = (centerMassPos.p - character['LeftFoot'].Position).magnitude

            local minY = minY1 > minY2 and minY1 or minY2
            local minX = x1 < x2 and x1 or x2

            local offsets = esp:returnoffsets(minX, y, minY, character['HumanoidRootPart'].Size.Z / 2)

            for i, v in next, offsets do
                local pos = camera:WorldToViewportPoint(centerMassPos * v.p)
                if smallestX > pos.X then smallestX = pos.X end
                if biggestX < pos.X then biggestX = pos.X end
                if smallestY > pos.Y then smallestY = pos.Y end
                if biggestY < pos.Y then biggestY = pos.Y end
            end

            -- box, healthbar, kevlarbar, distance, name, health, weapon (unchanged)
            drawing.box.Visible = esp[ flag .. 'boxes'][1]
            drawing.box_fill.Visible = drawing.box.Visible
            drawing.box_outline.Visible = esp.outlines and drawing.box.Visible
            if drawing.box.Visible then
                drawing.box.Color = esp[ flag .. 'boxes'][2]
                drawing.box.Size = esp:floorvector(NEWVEC2(biggestX - smallestX, biggestY - smallestY))
                drawing.box.Position = esp:floorvector(NEWVEC2(smallestX, smallestY))
                drawing.box.Transparency = transparency
                drawing.box_fill.Size = drawing.box.Size
                drawing.box_fill.Position = drawing.box.Position
                drawing.box_fill.Color = esp[ flag .. 'boxes'][3]
                drawing.box_fill.Transparency = MIN(esp[ flag .. 'boxes'][4], transparency)
                drawing.box_outline.Size = drawing.box.Size
                drawing.box_outline.Position = drawing.box.Position + NEWVEC2(1,1)
                drawing.box_outline.Transparency = transparency
            end

            drawing.bar.Visible = esp[ flag .. 'healthbar'][1]
            drawing.bar_inline.Visible = drawing.bar.Visible
            drawing.bar_outline.Visible = esp.outlines and drawing.bar.Visible
            if drawing.bar.Visible then
                drawing.bar.Color = esp[ flag .. 'healthbar'][3]:Lerp(esp[ flag .. 'healthbar'][2], health / 100)
                drawing.bar.Size = esp:floorvector(NEWVEC2(1, ( - health / 100 * ( biggestY - smallestY + 2)) + 3))
                drawing.bar.Position = esp:floorvector(NEWVEC2(smallestX - 3, smallestY + drawing.bar_outline.Size.Y))
                drawing.bar.Transparency = transparency
                drawing.bar_inline.Size = esp:floorvector(NEWVEC2(1, ( - 1 * ( biggestY - smallestY + 2)) + 3))
                drawing.bar_inline.Position = drawing.bar.Position
                drawing.bar_inline.Transparency = transparency
                drawing.bar_outline.Size = esp:floorvector(NEWVEC2(1, biggestY - smallestY))
                drawing.bar_outline.Position = esp:floorvector(NEWVEC2(smallestX - 2, smallestY + 1))
                drawing.bar_outline.Transparency = transparency
            end

            drawing.kevlarbar.Visible = esp[ flag .. 'kevlarbar'][1]
            drawing.kevlarbar_inline.Visible = drawing.kevlarbar.Visible
            drawing.kevlarbar_outline.Visible = esp.outlines and drawing.kevlarbar.Visible
            if drawing.kevlarbar.Visible then
                drawing.kevlarbar.Color = esp[ flag .. 'kevlarbar'][3]:Lerp(esp[ flag .. 'kevlarbar'][2], kevlar / 100)
                drawing.kevlarbar.Size = esp:floorvector(NEWVEC2(( kevlar / 100 * ( biggestX - smallestX)), 1))
                drawing.kevlarbar.Position = esp:floorvector(NEWVEC2(smallestX, biggestY + 2))
                drawing.kevlarbar.Transparency = transparency
                drawing.kevlarbar_inline.Size = esp:floorvector(NEWVEC2(( 1 * ( biggestX - smallestX)), 1))
                drawing.kevlarbar_inline.Position = drawing.kevlarbar.Position
                drawing.kevlarbar_inline.Transparency = transparency
                drawing.kevlarbar_outline.Size = esp:floorvector(NEWVEC2(biggestX - smallestX, 1))
                drawing.kevlarbar_outline.Position = esp:floorvector(NEWVEC2(smallestX + 1, biggestY + 3))
                drawing.kevlarbar_outline.Transparency = transparency
            end

            drawing.distance.Visible = not esp[ flag .. 'names'][1] and esp[ flag .. 'distance']
            drawing.distance_outline.Visible = esp.outlines and drawing.distance.Visible
            if drawing.distance.Visible then
                drawing.distance.Text = '['..distance..']'
                drawing.distance.Font = Drawing.Fonts[esp.font]
                drawing.distance.Size = esp.textsize
                drawing.distance.Color = esp[ flag .. 'names'][2]
                drawing.distance.Position = esp:floorvector(NEWVEC2(smallestX + (biggestX - smallestX) / 2 - (drawing.distance.TextBounds.X / 2), smallestY - drawing.distance.TextBounds.Y - 2))
                drawing.distance.Transparency = transparency
                drawing.distance_outline.Text = drawing.distance.Text
                drawing.distance_outline.Font = drawing.distance.Font
                drawing.distance_outline.Size = drawing.distance.Size
                drawing.distance_outline.Position = drawing.distance.Position + NEWVEC2(1,1)
                drawing.distance_outline.Transparency = transparency
            end

            drawing.name.Visible = esp[ flag .. 'names'][1]
            drawing.name_outline.Visible = esp.outlines and drawing.name.Visible
            if drawing.name.Visible then
                drawing.name.Text = esp[ flag .. 'distance'] and '['..distance..'] '..playerName or playerName
                drawing.name.Font = Drawing.Fonts[esp.font]
                drawing.name.Size = esp.textsize
                drawing.name.Color = esp[ flag .. 'names'][2]
                drawing.name.Position = esp:floorvector(NEWVEC2(smallestX + (biggestX - smallestX) / 2 - (drawing.name.TextBounds.X / 2), smallestY - drawing.name.TextBounds.Y - 2))
                drawing.name.Transparency = transparency
                drawing.name_outline.Text = drawing.name.Text
                drawing.name_outline.Font = drawing.name.Font
                drawing.name_outline.Size = drawing.name.Size
                drawing.name_outline.Position = drawing.name.Position + NEWVEC2(1,1)
                drawing.name_outline.Transparency = transparency
            end

            drawing.health.Visible = health ~= 100 and health ~= 0  and esp[flag .. 'health']
            if drawing.health.Visible then
                drawing.health.Text = tostring(health)
                drawing.health.Font = Drawing.Fonts[esp.font]
                drawing.health.Size = esp.textsize
                drawing.health.Outline = esp.outlines
                drawing.health.Color = esp[ flag .. 'healthbar'][3]:Lerp(esp[ flag .. 'healthbar'][2], health / 100)
                drawing.health.Position = esp:floorvector(NEWVEC2(smallestX - 3, drawing.bar.Position.Y + drawing.bar.Size.Y - drawing.health.TextBounds.Y + 5))
                drawing.health.Transparency = transparency
            end

            drawing.weapon.Visible = esp[ flag .. 'weapon'][1]
            drawing.weapon_outline.Visible = esp.outlines and drawing.weapon.Visible
            if drawing.weapon.Visible then
                drawing.weapon.Text = LOWER(character:GetAttribute("WhatGun")) or nil
                drawing.weapon.Font = Drawing.Fonts[esp.font]
                drawing.weapon.Size = esp.textsize
                drawing.weapon.Color = esp[ flag .. 'weapon'][2]
                drawing.weapon.Position = esp:floorvector(NEWVEC2(smallestX + (biggestX - smallestX) / 2 - (drawing.weapon.TextBounds.X / 2), biggestY + 4))
                drawing.weapon.Transparency = transparency
                drawing.weapon_outline.Text = drawing.weapon.Text
                drawing.weapon_outline.Font = drawing.weapon.Font
                drawing.weapon_outline.Size = drawing.weapon.Size
                drawing.weapon_outline.Position = drawing.weapon.Position + NEWVEC2(1,1)
                drawing.weapon_outline.Transparency = transparency
            end
        else
            esp:disable(player)
        end
    end
end

-- Initialize ESP
for i, plr in next, players:GetPlayers() do
    esp:add(plr)
end
esp:connect(players.PlayerAdded, function(plr)
    esp:add(plr)
end)
esp:connect(players.PlayerRemoving, function(plr)
    esp:remove(plr)
end)

esp:bindtorenderstep('esp', 999, esp.update)

-- ===============================
-- UI Callbacks for ESP (update esp table)
-- ===============================
EspEnabledLabel:AddToggle({
    Default = false,
    Callback = function(state)
        esp.enabled = state
    end,
    Flag = "esp_enabled"
})

TeamCheckLabel:AddToggle({
    Default = false,
    Callback = function(state)
        esp.teamcheck = state
    end,
    Flag = "esp_teamcheck"
})

OutlinesLabel:AddToggle({
    Default = false,
    Callback = function(state)
        esp.outlines = state
    end,
    Flag = "esp_outlines"
})

-- Chams (affects both team and enemy)
local ChamsToggle = ChamsLabel:AddToggle({
    Default = false,
    Callback = function(state)
        esp.team_chams[1] = state
        esp.enemy_chams[1] = state
        esp.priority_chams[1] = state
    end,
    Flag = "chams_enabled"
})
local ChamsOption = ChamsLabel:AddOption()
local ChamsFillColor = ChamsOption:AddLabel("Fill"):AddColorPicker({
    Default = Color3.fromRGB(138, 139, 194),
    Flag = "chams_fill_color",
    Callback  = function(state)
        esp.team_chams[2] = state
        esp.enemy_chams[2] = state
        esp.priority_chams[2] = state
    end,
})
local ChamsOutlineColor = ChamsOption:AddLabel("Outline"):AddColorPicker({
    Default = Color3.fromRGB(138, 139, 194),
    Flag = "chams_outline_color",
    Callback  = function(state)
        esp.team_chams[3] = state
        esp.enemy_chams[3] = state
        esp.priority_chams[3] = state
    end,
})
local ChamsFillTransparency = ChamsOption:AddLabel("FillTrans"):AddSlider({
    Default = 0.25,
    Min = 0,
    Max = 1,
    Rounding = 1,
    Flag = "chams_fill_trans",
    Callback = function(state)
        esp.team_chams[4] = state
        esp.enemy_chams[4] = state
        esp.priority_chams[4] = state
    end,
})
local ChamsOutlineTransparency = ChamsOption:AddLabel("OutlineTrans"):AddSlider({
    Default = 0.75,
    Min = 0,
    Max = 1,
    Rounding = 1,
    Flag = "chams_outline_trans",
    Callback = function(state)
        esp.team_chams[5] = state
        esp.enemy_chams[5] = state
        esp.priority_chams[5] = state
    end,
})
local ChamsDepth = ChamsOption:AddLabel("Depth"):AddSlider({
    Default = 0,
    Min = 0,
    Max = 1,
    Rounding = 0,
    Flag = "chams_depth",
    Callback = function(state)
        esp.team_chams[6] = state
        esp.enemy_chams[6] = state
        esp.priority_chams[6] = state
    end,
})

-- Weapon Name
local WeaponNameToggle = ShowWeaponName:AddToggle({
    Default = false,
    Callback = function(state)
        esp.team_weapon[1] = state
        esp.enemy_weapon[1] = state
        esp.priority_weapon[1] = state
    end,
    Flag = "weapon_name_enabled"
})
local WeaponNameOption = ShowWeaponName:AddOption()
local WeaponNameColor = WeaponNameOption:AddLabel("Color"):AddColorPicker({
    Default = Color3.fromRGB(255, 255, 255),
    Flag = "weapon_name_color",
    Callback  = function(state)
        esp.team_weapon[2] = state
        esp.enemy_weapon[2] = state
        esp.priority_weapon[2] = state
    end,
})

-- Health
ShowHealth:AddToggle({
    Default = false,
    Callback  = function(state)
        esp.team_health = state
        esp.enemy_health = state
        esp.priority_health = state
    end,
    Flag = "show_health"
})

-- Distance
ShowDistance:AddToggle({
    Default = false,
    Callback  = function(state)
        esp.team_distance = state
        esp.enemy_distance = state
        esp.priority_distance = state
    end,
    Flag = "show_distance"
})

-- Names
local NameToggle = ShowNames:AddToggle({
    Default = false,
    Callback = function(state)
        esp.team_names[1] = state
        esp.enemy_names[1] = state
        esp.priority_names[1] = state
    end,
    Flag = "show_names_enabled"
})
local NameOption = ShowNames:AddOption()
local NameColor = NameOption:AddLabel("Color"):AddColorPicker({
    Default = Color3.fromRGB(255, 255, 255),
    Flag = "name_color",
    Callback  = function(state)
        esp.team_names[2] = state
        esp.enemy_names[2] = state
        esp.priority_names[2] = state
    end,
})

-- ===============================
-- Weapon mods (unchanged)
-- ===============================
RecoilLabel:AddToggle({
    Default = false,
    Callback = function (state) return state end
})
RecoilLabel:ToolTip("Lower Better")
local RecoilOption = RecoilLabel:AddOption()
local recoilX = RecoilOption:AddLabel("X"):AddSlider({
    Default = nil,
    Min = 0,
    Max = 100,
    Type = "%",
    Rounding = 0,
    Flag = "MySlider",
    Size = 125,
    Callback = function(value)
        for _, recoil in weapons do
            recoil:SetAttribute("RecoilX", value)
        end
    end,
})
local recoily = RecoilOption:AddLabel("Y"):AddSlider({
    Default = nil,
    Min = 0,
    Max = 100,
    Type = "%",
    Rounding = 0,
    Flag = "MySlider",
    Size = 125,
    Callback = function(value)
        for _, recoil in weapons do
            recoil:SetAttribute("RecoilY", value)
        end
    end,
})

SpreadLabel:AddToggle({
    Default = false,
    Callback = function (state) return state end
})
SpreadLabel:ToolTip("Tightness of crosshair, lower = tighter?")
local SpreadOption = SpreadLabel:AddOption()
local Spread = SpreadOption:AddLabel("Spread"):AddSlider({
    Default = nil,
    Min = 0,
    Max = 100,
    Type = "%",
    Rounding = 0,
    Flag = "MySlider",
    Size = 125,
    Callback = function(value)
        for _, spread in weapons do
            spread:SetAttribute("Spread", value)
        end
    end,
})
local AimSpread = SpreadOption:AddLabel("AimSpread"):AddSlider({
    Default = nil,
    Min = 0,
    Max = 100,
    Type = "%",
    Rounding = 0,
    Flag = "MySlider",
    Size = 125,
    Callback = function(value)
        for _, spread in weapons do
            spread:SetAttribute("AimSpread", value)
        end
    end,
})

FireRateLabel:AddToggle({
    Default = false,
    Callback = function (state) return state end
})
FireRateLabel:ToolTip("Modify Rate, Low Number Faster")
local FireRateOption = FireRateLabel:AddOption()
local FireRate = FireRateOption:AddLabel("FireRate"):AddSlider({
    Default = nil,
    Min = -10,
    Max = 100,
    Type = "%",
    Rounding = 0,
    Flag = "MySlider",
    Size = 125,
    Callback = function(value)
        for _, rate in weapons do
            rate:SetAttribute("FireRate", value)
        end
    end,
})

AmmoLabel:AddToggle({
    Default = false,
    Callback = function (state) return state end
})
local AmmoOption = AmmoLabel:AddOption()
local Ammo = AmmoOption:AddLabel("Ammo"):AddSlider({
    Default = nil,
    Min = 0,
    Max = 300,
    Type = "",
    Rounding = 0,
    Flag = "MySlider",
    Size = 125,
    Callback = function(value)
        for _, ammo_w in weapons do
            ammo_w:SetAttribute("Ammo", value)
        end
    end,
})
local StoredAmmo = AmmoOption:AddLabel("StoredAmmo"):AddSlider({
    Default = nil,
    Min = 0,
    Max = 300,
    Type = "",
    Rounding = 0,
    Flag = "MySlider",
    Size = 100,
    Callback = function(value)
        for _, stored in weapons do
            stored:SetAttribute("StoredAmmo", value)
        end
    end,
})

TimesLabel:AddToggle({
    Default = false,
    Callback = function (state) return state end
})
TimesLabel:ToolTip("Modify Spread, Lower Faster")
local TimesOption = TimesLabel:AddOption()
local AimTime = TimesOption:AddLabel("AimTime"):AddSlider({
    Default = nil,
    Min = 0,
    Max = 51,
    Type = "%",
    Rounding = 1,
    Flag = "MySlider",
    Size = 100,
    Callback = function(value)
        for _, aimtime in weapons do
            aimtime:SetAttribute("AimTime", value)
        end
    end,
})
local EquipTime = TimesOption:AddLabel("EquipTime"):AddSlider({
    Default = nil,
    Min = 0,
    Max = 51,
    Type = "%",
    Rounding = 1,
    Flag = "MySlider",
    Size = 100,
    Callback = function(value)
        for _, equiptime in weapons do
            equiptime:SetAttribute("EquipTime", value)
        end
    end,
})
local EReloadTime = TimesOption:AddLabel("EReloadTime"):AddSlider({
    Default = nil,
    Min = 0,
    Max = 51,
    Type = "%",
    Rounding = 1,
    Flag = "MySlider",
    Size = 100,
    Callback = function(value)
        for _, ereloadtime in weapons do
            ereloadtime:SetAttribute("EReloadTime", value)
        end
    end,
})
local ReloadTime = TimesOption:AddLabel("ReloadTime"):AddSlider({
    Default = nil,
    Min = 0,
    Max = 51,
    Type = "%",
    Rounding = 1,
    Flag = "MySlider",
    Size = 100,
    Callback = function(value)
        for _, reloadtime in weapons do
            reloadtime:SetAttribute("ReloadTime", value)
        end
    end,
})

PenetrationLabel:AddToggle({
    Default = false,
    Callback = function (state) return state end
})
local PenetrationOption = PenetrationLabel:AddOption()
local Penetration = PenetrationOption:AddLabel("Pentration"):AddSlider({
    Default = nil,
    Min = 0,
    Max = 100,
    Type = "",
    Rounding = 1,
    Flag = "MySlider",
    Size = 125,
    Callback = function(value)
        for _, pen in weapons do
            pen:SetAttribute("Penetration", value)
        end
    end,
})
AutomaticLabel:AddToggle({
    Default = false,
    Callback = function(state)
        for _, auto in weapons do
            auto:SetAttribute("Auto", state)
        end
    end
})
WeaponSpeedLabel:AddToggle({
    Default = false,
    Callback = function (state)
        
    end
})
WeaponSpeedLabel:ToolTip("Modify WalkSpeed (Multiples WalkSpeed)")
local WeaponSpeedOption = WeaponSpeedLabel:AddOption()
local WeaponWalkSpeed = WeaponSpeedOption:AddLabel("WalkSpeed"):AddSlider({
    Default = nil,
    Min = 0,
    Max = 100,
    Type = "%",
    Rounding = 0,
    Flag = "MySlider",
    Size = 125,
    Callback = function(value)
        for _, walkspeed in weapons do
            walkspeed:SetAttribute("WalkSpeed", value)
        end
    end,
})
local WeaponAimSpeed = WeaponSpeedOption:AddLabel("AimSpeed"):AddSlider({
    Default = nil,
    Min = 0,
    Max = 100,
    Type = "%",
    Rounding = 0,
    Flag = "MySlider",
    Size = 125,
    Callback = function(value)
        for _, aimspeed in weapons do
            aimspeed:SetAttribute("AimWalkSpeed", value)
        end
end,
})
BulletsLabel:AddSlider({
    Default = nil,
    Min = 1,
    Max = 51,
    Type = "",
    Rounding = 0,
    Flag = "MySlider",
    Size = 125,
    Callback = function(value)
        for _, bullet in weapons do
            bullet:SetAttribute("Bullets", value)
        end
end,
})
BlastRadiusLabel:AddSlider({
    Default = nil,
    Min = 1,
    Max = 500,
    Type = "",
    Rounding = 0,
    Flag = "MySlider",
    Size = 100,
    Callback = function(value)
        for _, bullet in weapons do
            bullet:SetAttribute("BlastRadius", value)
        end
end,
})
ProjectileSpeedLabel:AddSlider({
    Default = nil,
    Min = 1,
    Max = 500,
    Type = "",
    Rounding = 0,
    Flag = "MySlider",
    Size = 100,
    Callback = function(value)
        for _, projectileSpeed in weapons do
            projectileSpeed:SetAttribute("ProjectileSpeed", value)
        end
end,
})

-- ===============================
-- Grenade Notification (unchanged)
-- ===============================
local monitoring = false
local monitorThread = nil
local notifiedGrenades = {}

local exactBlacklist = {
    "Casing",
    "Helicopter",
    "Flare",
    "Predator Missile",
    "Overwatch Helo"
    -- add other exact names you want to ignore
}

local function isBlacklisted(name)
    -- Check exact matches
    for _, item in ipairs(exactBlacklist) do
        if name == item then
            return true
        end
    end
    -- Check pattern: starts with "Ragdoll_"
    if string.sub(name, 1, 8) == "Ragdoll_" then
        return true
    end
    return false
end

local NotificationToggle = Notify:AddToggle({
    Default = false,
    Callback = function(state)
        print("Notification toggle:", state)
        if state == true then
            if monitoring then
                monitoring = false
                monitorThread = nil
            end
            for nade, highlight in pairs(notifiedGrenades) do
                if highlight and highlight.Parent then
                    highlight:Destroy()
                end
            end
            notifiedGrenades = {}

            monitoring = true
            monitorThread = task.spawn(function()
                while monitoring do
                    local nades = getFrags()
                    if nades then
                        for _, nade in ipairs(nades) do
                            if not notifiedGrenades[nade] then
                                -- Skip if blacklisted
                                if isBlacklisted(nade.Name) then
                                    continue
                                end

                                local highlight = Instance.new("Highlight")
                                highlight.Name = "_X"
                                highlight.FillColor = Color3.fromRGB(241, 167, 225)
                                highlight.FillTransparency = 0.3
                                highlight.OutlineColor = Color3.fromRGB(255, 255, 255)
                                highlight.OutlineTransparency = 1
                                highlight.DepthMode = Enum.HighlightDepthMode.AlwaysOnTop
                                highlight.Adornee = nade
                                highlight.Parent = nade

                                notifiedGrenades[nade] = highlight

                                if nade:IsA("BasePart") then
                                    nade.Transparency = 0
                                end

                                Notification.new({
                                    Title = nade.Name,
                                    Content = nade.Name,
                                    Duration = 1.5,
                                })
                            end
                        end
                    end
                    task.wait(0.1)
                end

                for nade, highlight in pairs(notifiedGrenades) do
                    if highlight and highlight.Parent then
                        highlight:Destroy()
                    end
                end
                notifiedGrenades = {}
                monitoring = false
                monitorThread = nil
                print("Monitoring stopped")
            end)
        else
            monitoring = false
            monitorThread = nil
            for nade, highlight in pairs(notifiedGrenades) do
                if highlight and highlight.Parent then
                    highlight:Destroy()
                end
            end
            notifiedGrenades = {}
            print("Monitoring stopped by toggle off")
        end
    end,
    Flag = "grenade_notify"
})
-- ===============================
-- STANDALONE RAYCAST SILENT AIM (Integrated)
-- ===============================

-- Cached functions (optimized)
local GetPlayers = Players.GetPlayers
local WorldToScreen = Camera.WorldToScreenPoint
local GetPartsObscuringTarget = Camera.GetPartsObscuringTarget
local FindFirstChild = game.FindFirstChild

-- Helper: get mouse position
local function getMousePosition()
    return Vector2.new(mouse.X, mouse.Y)
end

-- Helper: screen position of a world point
local function getPositionOnScreen(Vector)
    local Vec3, OnScreen = WorldToScreen(Camera, Vector)
    return Vector2.new(Vec3.X, Vec3.Y), OnScreen
end

-- Visibility check using Camera:GetPartsObscuringTarget
local function IsPlayerVisible(Player)
    local PlayerCharacter = Player.Character
    local LocalPlayerCharacter = localPlayer.Character
    if not (PlayerCharacter and LocalPlayerCharacter) then return false end

    local targetRoot = FindFirstChild(PlayerCharacter, "HumanoidRootPart") or PlayerCharacter.PrimaryPart
    if not targetRoot then return false end

    local origin = FindFirstChild(LocalPlayerCharacter, "HumanoidRootPart") or LocalPlayerCharacter.PrimaryPart
    if not origin then return false end

    local CastPoints = {targetRoot.Position, origin.Position}
    local IgnoreList = {LocalPlayerCharacter, PlayerCharacter}
    local ObscuringObjects = #GetPartsObscuringTarget(Camera, CastPoints, IgnoreList)
    return ObscuringObjects == 0
end

-- Get closest enemy inside FOV circle, respecting Wallbang
local function getClosestPlayer()
    local Closest
    local DistanceToMouse

    for _, Player in next, GetPlayers(Players) do
        if Player == localPlayer then continue end

        local Character = Player.Character
        if not Character then continue end

        -- FIXED WALLBANG LOGIC
        local wallbangOn = WallbangToggle and WallbangToggle:GetValue() or false
        if not wallbangOn then
            -- Wallbang OFF: player must be visible
            if not IsPlayerVisible(Player) then continue end
        end
        -- If wallbangOn is true, we ignore visibility

        local HumanoidRootPart = FindFirstChild(Character, "HumanoidRootPart")
        local Humanoid = FindFirstChild(Character, "Humanoid")
        if not HumanoidRootPart or not Humanoid or Humanoid.Health <= 0 then continue end

        local ScreenPosition, OnScreen = getPositionOnScreen(HumanoidRootPart.Position)
        if not OnScreen then continue end

        -- FOV check using your circle
        local Distance = (getMousePosition() - ScreenPosition).Magnitude
        if Distance <= (DistanceToMouse or aimbotCircle.Radius or 2000) then
            Closest = HumanoidRootPart
            DistanceToMouse = Distance
        end
    end
    return Closest
end

-- Expected arguments for Raycast
local ExpectedArguments = {
    Raycast = {
        ArgCountRequired = 3,
        Args = {
            "Instance", "Vector3", "Vector3", "RaycastParams"
        }
    }
}

-- Validate arguments
local function ValidateArguments(Args, RayMethod)
    local Matches = 0
    if #Args < RayMethod.ArgCountRequired then
        return false
    end
    for Pos, Argument in next, Args do
        if typeof(Argument) == RayMethod.Args[Pos] then
            Matches = Matches + 1
        end
    end
    return Matches >= RayMethod.ArgCountRequired
end

-- Get direction
local function getDirection(Origin, Position)
    return (Position - Origin).Unit * 1000
end

-- ===============================
-- RAYCAST HOOK (Only Raycast)
-- ===============================
local oldNamecall
oldNamecall = hookmetamethod(game, "__namecall", newcclosure(function(...)
    local Method = getnamecallmethod()
    local Arguments = {...}
    local self = Arguments[1]

    -- Only intervene when SilentToggle is ON and call is on workspace
    if SilentToggle and SilentToggle:GetValue() and self == workspace and not checkcaller() then
        if Method == "Raycast" then
            if ValidateArguments(Arguments, ExpectedArguments.Raycast) then
                local A_Origin = Arguments[2]
                local HitPart = getClosestPlayer()
                if HitPart then
                    Arguments[3] = getDirection(A_Origin, HitPart.Position)
                    return oldNamecall(unpack(Arguments))
                end
            end
        end
    end

    return oldNamecall(...)
end))

task.spawn(function()
	while true do task.wait(1)
		ping:SetText(tostring(math.random(30,90))..'MS')
	end
end)

-- ===============================
-- SCRIPT END
-- ===============================

Features & Information

w

Community Comments (0)

No comments yet for this script.

More Scripts for [FPS] Enforcement