--[[ CLIENT ESP CONTROL PANEL — REFINED Original features preserved. Performance caps, cleanup, and local prompt restoration added. Run as a LocalScript in Roblox Studio for an experience you own or have permission to test. All ESP categories begin disabled. Teleports are client-side and may be corrected by the server. ]] --// CLIENT ESP CONTROL PANEL --// Original-style GUI + newer functions + Waypoints --// All ESP toggles start OFF --// Automatic scan every 5 seconds --// Draggable window --// Kill GUI stops scanning and removes ESP visuals and waypoints local Players = game:GetService("Players") local Workspace = game:GetService("Workspace") local CollectionService = game:GetService("CollectionService") local UserInputService = game:GetService("UserInputService") local RunService = game:GetService("RunService") local Lighting = game:GetService("Lighting") local Stats = game:GetService("Stats") local TeleportService = game:GetService("TeleportService") local player = Players.LocalPlayer local playerGui = player:WaitForChild("PlayerGui") local SCAN_INTERVAL = 5 local PROX_UPDATE_INTERVAL = 1 local PLAYER_UPDATE_INTERVAL = 0.5 local MAX_ESP_TARGETS = 150 local previousShutdown = _G.__ClientESPPanelShutdown if type(previousShutdown) == "function" then pcall(previousShutdown) end local running = true local scanQueued = false local scanning = false local MAX_WAYPOINTS = 25 local OPTIONS = { PromptsEnabled = false, ProximityPrompts = false, ClickDetectors = false, TaggedObjects = false, Collectibles = false, Tools = false, UnanchoredParts = false, ShowHighlights = false, ShowLabels = false, ShowDistance = false, ThroughWalls = false, RedAfterInteraction = false, ShowWaypoints = false, WaypointLines = false, AutoDeathWaypoint = false, PlayerESP = false, PlayerDisplayNames = false, ProxPrompts = false, ProxTouch = false, ProxSeats = false, ProxItems = false, ClickTeleport = false, } local COLORS = { Cyan = Color3.fromRGB(0, 200, 255), Red = Color3.fromRGB(255, 55, 55), Green = Color3.fromRGB(80, 255, 100), Yellow = Color3.fromRGB(255, 220, 50), Purple = Color3.fromRGB(190, 90, 255), } local colorNames = {"Cyan", "Red", "Green", "Yellow", "Purple"} local colorIndex = 1 local tracked = {} local playerCharacters = {} local interacted = setmetatable({}, {__mode = "k"}) local connections = {} local promptOriginal = setmetatable({}, {__mode = "k"}) local promptChangeConnection local promptAddedConnection local trackedCount = 0 --// GUI SETUP local gui = Instance.new("ScreenGui") gui.Name = "ClientESPControlPanel" gui.ResetOnSpawn = false gui.IgnoreGuiInset = true gui.DisplayOrder = 50 gui.Parent = playerGui local main = Instance.new("Frame") main.Name = "Main" main.Size = UDim2.fromOffset(340, 580) main.Position = UDim2.new(0, 25, 0.5, -290) main.BackgroundColor3 = Color3.fromRGB(24, 24, 32) main.BorderSizePixel = 0 main.ClipsDescendants = true main.Parent = gui local mainCorner = Instance.new("UICorner") mainCorner.CornerRadius = UDim.new(0, 9) mainCorner.Parent = main local mainStroke = Instance.new("UIStroke") mainStroke.Color = Color3.fromRGB(75, 75, 95) mainStroke.Thickness = 1 mainStroke.Parent = main --// Draggable title bar local titleBar = Instance.new("Frame") titleBar.Name = "TitleBar" titleBar.Size = UDim2.new(1, 0, 0, 48) titleBar.BackgroundColor3 = Color3.fromRGB(34, 34, 46) titleBar.BorderSizePixel = 0 titleBar.Active = true titleBar.Parent = main local title = Instance.new("TextLabel") title.Size = UDim2.new(1, -90, 1, 0) title.Position = UDim2.fromOffset(12, 0) title.BackgroundTransparency = 1 title.Text = "ESP CONTROL PANEL" title.TextColor3 = Color3.fromRGB(240, 240, 255) title.Font = Enum.Font.GothamBold title.TextSize = 16 title.TextXAlignment = Enum.TextXAlignment.Left title.Parent = titleBar local closeButton = Instance.new("TextButton") closeButton.Name = "CloseButton" closeButton.Size = UDim2.fromOffset(32, 30) closeButton.Position = UDim2.new(1, -38, 0, 9) closeButton.BackgroundColor3 = Color3.fromRGB(145, 45, 50) closeButton.Text = "X" closeButton.TextColor3 = Color3.new(1, 1, 1) closeButton.Font = Enum.Font.GothamBold closeButton.TextSize = 14 closeButton.Parent = titleBar Instance.new("UICorner", closeButton).CornerRadius = UDim.new(0, 5) local minimizeButton = Instance.new("TextButton") minimizeButton.Name = "MinimizeButton" minimizeButton.Size = UDim2.fromOffset(32, 30) minimizeButton.Position = UDim2.new(1, -76, 0, 9) minimizeButton.BackgroundColor3 = Color3.fromRGB(60, 60, 82) minimizeButton.Text = "-" minimizeButton.TextColor3 = Color3.new(1, 1, 1) minimizeButton.Font = Enum.Font.GothamBold minimizeButton.TextSize = 16 minimizeButton.Parent = titleBar Instance.new("UICorner", minimizeButton).CornerRadius = UDim.new(0, 5) local subtitle = Instance.new("TextLabel") subtitle.Size = UDim2.new(1, -20, 0, 22) subtitle.Position = UDim2.fromOffset(10, 49) subtitle.BackgroundTransparency = 1 subtitle.Text = "ESP OFF by default | RightCtrl toggles panel" subtitle.TextColor3 = Color3.fromRGB(165, 165, 180) subtitle.Font = Enum.Font.Gotham subtitle.TextSize = 11 subtitle.Parent = main local tabBar = Instance.new("Frame") tabBar.Name = "TabBar" tabBar.Position = UDim2.fromOffset(9, 73) tabBar.Size = UDim2.new(1, -18, 0, 56) tabBar.BackgroundTransparency = 1 tabBar.Parent = main local tabGrid = Instance.new("UIGridLayout") tabGrid.CellSize = UDim2.new(0.25, -4, 0, 26) tabGrid.CellPadding = UDim2.fromOffset(4, 4) tabGrid.SortOrder = Enum.SortOrder.LayoutOrder tabGrid.Parent = tabBar local content = Instance.new("Frame") content.Name = "Pages" content.Position = UDim2.fromOffset(9, 134) content.Size = UDim2.new(1, -18, 1, -180) content.BackgroundTransparency = 1 content.ClipsDescendants = true content.Parent = main local status = Instance.new("TextLabel") status.Name = "Status" status.Position = UDim2.new(0, 10, 1, -38) status.Size = UDim2.new(1, -20, 0, 25) status.BackgroundTransparency = 1 status.Text = "Ready — ESP disabled" status.TextColor3 = Color3.fromRGB(140, 220, 155) status.Font = Enum.Font.Gotham status.TextSize = 11 status.TextXAlignment = Enum.TextXAlignment.Left status.Parent = main --// Minimize local minimized = false minimizeButton.Activated:Connect(function() minimized = not minimized content.Visible = not minimized tabBar.Visible = not minimized status.Visible = not minimized subtitle.Visible = not minimized main.Size = minimized and UDim2.fromOffset(340, 48) or UDim2.fromOffset(340, 580) minimizeButton.Text = minimized and "+" or "-" end) --// Drag handling local dragging = false local dragStart local startPosition local dragInput titleBar.InputBegan:Connect(function(input) if input.UserInputType == Enum.UserInputType.MouseButton1 or input.UserInputType == Enum.UserInputType.Touch then dragging = true dragStart = input.Position startPosition = main.Position input.Changed:Connect(function() if input.UserInputState == Enum.UserInputState.End then dragging = false end end) end end) titleBar.InputChanged:Connect(function(input) if input.UserInputType == Enum.UserInputType.MouseMovement or input.UserInputType == Enum.UserInputType.Touch then dragInput = input end end) local dragConnection = UserInputService.InputChanged:Connect(function(input) if dragging and input == dragInput then local delta = input.Position - dragStart main.Position = UDim2.new( startPosition.X.Scale, startPosition.X.Offset + delta.X, startPosition.Y.Scale, startPosition.Y.Offset + delta.Y ) end end) --// Hide / show hotkey local keyConnection = UserInputService.InputBegan:Connect(function(input, processed) if processed then return end if input.KeyCode == Enum.KeyCode.RightControl then main.Visible = not main.Visible end end) --// Helpers --// TABS + COLLAPSIBLE SECTIONS local pages = {} local tabButtons = {} local tabOrder = 0 local currentPage local currentBody local allSections = {} local TAB_ACTIVE = Color3.fromRGB(70, 90, 160) local TAB_IDLE = Color3.fromRGB(44, 44, 60) local function uiParent() return currentBody or currentPage end local function setTab(name) for tabName, page in pairs(pages) do page.Visible = tabName == name tabButtons[tabName].BackgroundColor3 = tabName == name and TAB_ACTIVE or TAB_IDLE end end local function newTab(name, text) tabOrder += 1 local button = Instance.new("TextButton") button.Name = name .. "Tab" button.LayoutOrder = tabOrder button.BackgroundColor3 = TAB_IDLE button.Text = text button.TextColor3 = Color3.fromRGB(235, 235, 250) button.Font = Enum.Font.GothamBold button.TextSize = 11 button.Parent = tabBar Instance.new("UICorner", button).CornerRadius = UDim.new(0, 5) local page = Instance.new("ScrollingFrame") page.Name = name .. "Page" page.Size = UDim2.fromScale(1, 1) page.BackgroundTransparency = 1 page.BorderSizePixel = 0 page.ScrollBarThickness = 4 page.ScrollBarImageColor3 = Color3.fromRGB(115, 115, 145) page.AutomaticCanvasSize = Enum.AutomaticSize.Y page.CanvasSize = UDim2.new() page.ScrollingDirection = Enum.ScrollingDirection.Y page.Visible = false page.Parent = content local pageLayout = Instance.new("UIListLayout") pageLayout.Padding = UDim.new(0, 6) pageLayout.SortOrder = Enum.SortOrder.LayoutOrder pageLayout.Parent = page local pagePadding = Instance.new("UIPadding") pagePadding.PaddingTop = UDim.new(0, 3) pagePadding.PaddingBottom = UDim.new(0, 5) pagePadding.PaddingLeft = UDim.new(0, 3) pagePadding.PaddingRight = UDim.new(0, 3) pagePadding.Parent = page pages[name] = page tabButtons[name] = button button.Activated:Connect(function() setTab(name) end) end local function useTab(name) currentPage = pages[name] currentBody = nil end local function section(text) local container = Instance.new("Frame") container.Size = UDim2.new(1, -4, 0, 0) container.AutomaticSize = Enum.AutomaticSize.Y container.BackgroundTransparency = 1 container.Parent = currentPage local containerLayout = Instance.new("UIListLayout") containerLayout.Padding = UDim.new(0, 4) containerLayout.SortOrder = Enum.SortOrder.LayoutOrder containerLayout.Parent = container local header = Instance.new("TextButton") header.Size = UDim2.new(1, 0, 0, 25) header.LayoutOrder = 1 header.BackgroundColor3 = Color3.fromRGB(39, 39, 53) header.TextColor3 = Color3.fromRGB(200, 200, 220) header.Font = Enum.Font.GothamBold header.TextSize = 11 header.TextXAlignment = Enum.TextXAlignment.Left header.Parent = container Instance.new("UICorner", header).CornerRadius = UDim.new(0, 5) local body = Instance.new("Frame") body.Size = UDim2.new(1, 0, 0, 0) body.AutomaticSize = Enum.AutomaticSize.Y body.BackgroundTransparency = 1 body.LayoutOrder = 2 body.Parent = container local bodyLayout = Instance.new("UIListLayout") bodyLayout.Padding = UDim.new(0, 5) bodyLayout.SortOrder = Enum.SortOrder.LayoutOrder bodyLayout.Parent = body local collapsed = false local function setCollapsed(state) collapsed = state body.Visible = not state header.Text = (state and " [+] " or " [-] ") .. text end setCollapsed(false) header.Activated:Connect(function() setCollapsed(not collapsed) end) table.insert(allSections, setCollapsed) currentBody = body return body end local function makeButton(text, color) local button = Instance.new("TextButton") button.Size = UDim2.new(1, -4, 0, 30) button.BackgroundColor3 = color or Color3.fromRGB(47, 47, 62) button.TextColor3 = Color3.fromRGB(245, 245, 250) button.Font = Enum.Font.Gotham button.TextSize = 12 button.Text = text button.AutoButtonColor = true button.Parent = uiParent() Instance.new("UICorner", button).CornerRadius = UDim.new(0, 5) return button end --// SLIDERS + TEXT BOXES local activeSlider local sliderMoveConnection = UserInputService.InputChanged:Connect(function(input) if activeSlider and (input.UserInputType == Enum.UserInputType.MouseMovement or input.UserInputType == Enum.UserInputType.Touch) then activeSlider(input.Position.X) end end) local sliderEndConnection = UserInputService.InputEnded:Connect(function(input) if input.UserInputType == Enum.UserInputType.MouseButton1 or input.UserInputType == Enum.UserInputType.Touch then activeSlider = nil end end) local function makeSlider(label, minValue, maxValue, defaultValue, decimals, callback) local holder = Instance.new("Frame") holder.Size = UDim2.new(1, -4, 0, 44) holder.BackgroundColor3 = Color3.fromRGB(34, 34, 46) holder.BorderSizePixel = 0 holder.Parent = uiParent() Instance.new("UICorner", holder).CornerRadius = UDim.new(0, 5) local titleLabel = Instance.new("TextLabel") titleLabel.Size = UDim2.new(1, -16, 0, 16) titleLabel.Position = UDim2.fromOffset(8, 4) titleLabel.BackgroundTransparency = 1 titleLabel.TextColor3 = Color3.fromRGB(225, 225, 240) titleLabel.Font = Enum.Font.Gotham titleLabel.TextSize = 12 titleLabel.TextXAlignment = Enum.TextXAlignment.Left titleLabel.Parent = holder local track = Instance.new("Frame") track.Position = UDim2.new(0, 10, 0, 29) track.Size = UDim2.new(1, -20, 0, 6) track.BackgroundColor3 = Color3.fromRGB(62, 62, 84) track.BorderSizePixel = 0 track.Parent = holder Instance.new("UICorner", track).CornerRadius = UDim.new(1, 0) local fill = Instance.new("Frame") fill.Size = UDim2.fromScale(0, 1) fill.BackgroundColor3 = Color3.fromRGB(85, 145, 255) fill.BorderSizePixel = 0 fill.Parent = track Instance.new("UICorner", fill).CornerRadius = UDim.new(1, 0) local knob = Instance.new("Frame") knob.Size = UDim2.fromOffset(14, 14) knob.AnchorPoint = Vector2.new(0.5, 0.5) knob.Position = UDim2.fromScale(0, 0.5) knob.BackgroundColor3 = Color3.new(1, 1, 1) knob.BorderSizePixel = 0 knob.Parent = track Instance.new("UICorner", knob).CornerRadius = UDim.new(1, 0) local hit = Instance.new("TextButton") hit.Position = UDim2.fromOffset(0, 20) hit.Size = UDim2.new(1, 0, 0, 24) hit.BackgroundTransparency = 1 hit.Text = "" hit.AutoButtonColor = false hit.Parent = holder local value = defaultValue local function setValue(newValue, silent) newValue = math.clamp(newValue, minValue, maxValue) local factor = 10 ^ decimals newValue = math.floor(newValue * factor + 0.5) / factor value = newValue local alpha = (newValue - minValue) / (maxValue - minValue) fill.Size = UDim2.new(alpha, 0, 1, 0) knob.Position = UDim2.new(alpha, 0, 0.5, 0) titleLabel.Text = label .. ": " .. tostring(newValue) if not silent and callback then callback(newValue) end end local function fromX(x) local alpha = math.clamp( (x - track.AbsolutePosition.X) / math.max(track.AbsoluteSize.X, 1), 0, 1 ) setValue(minValue + (maxValue - minValue) * alpha) end hit.InputBegan:Connect(function(input) if input.UserInputType == Enum.UserInputType.MouseButton1 or input.UserInputType == Enum.UserInputType.Touch then activeSlider = fromX fromX(input.Position.X) end end) setValue(defaultValue, true) return { set = setValue, get = function() return value end, } end local function makeTextBox(placeholder, callback) local box = Instance.new("TextBox") box.Size = UDim2.new(1, -4, 0, 30) box.BackgroundColor3 = Color3.fromRGB(47, 47, 62) box.PlaceholderText = placeholder box.PlaceholderColor3 = Color3.fromRGB(140, 140, 160) box.Text = "" box.TextColor3 = Color3.fromRGB(235, 235, 250) box.Font = Enum.Font.Gotham box.TextSize = 12 box.ClearTextOnFocus = false box.Parent = uiParent() Instance.new("UICorner", box).CornerRadius = UDim.new(0, 5) box.FocusLost:Connect(function() callback(box.Text) end) return box end local function targetColor(instance) if OPTIONS.RedAfterInteraction and interacted[instance] then return COLORS.Red end return COLORS[colorNames[colorIndex]] end local function isPrompt(instance) return instance:IsA("ProximityPrompt") end local function isClickDetector(instance) return instance:IsA("ClickDetector") end local function isCollectible(instance) local name = instance.Name:lower() return name:find("coin", 1, true) or name:find("currency", 1, true) or name:find("collectible", 1, true) or name:find("token", 1, true) or name:find("gem", 1, true) end local function getTarget(instance) if isPrompt(instance) or isClickDetector(instance) then return instance.Parent end return instance end local function refreshPlayerCharacters() table.clear(playerCharacters) for _, plr in ipairs(Players:GetPlayers()) do if plr.Character then playerCharacters[plr.Character] = true end end end local function isPlayerCharacterPart(instance) local current = instance.Parent while current and current ~= Workspace do if playerCharacters[current] then return true end current = current.Parent end return false end local function isTarget(instance) if OPTIONS.ProximityPrompts and isPrompt(instance) then return true end if OPTIONS.ClickDetectors and isClickDetector(instance) then return true end if OPTIONS.TaggedObjects and CollectionService:HasTag(instance, "Interactable") then return true end if OPTIONS.Collectibles and isCollectible(instance) then return true end if OPTIONS.Tools and instance:IsA("Tool") then return true end if OPTIONS.UnanchoredParts and instance:IsA("BasePart") and not instance.Anchored and not isPlayerCharacterPart(instance) then return true end return false end local function removeVisuals(instance) local data = tracked[instance] if not data then return end if data.highlight then data.highlight:Destroy() end if data.billboard then data.billboard:Destroy() end tracked[instance] = nil end local function markInteracted(instance) if not instance then return end interacted[instance] = true local data = tracked[instance] if OPTIONS.RedAfterInteraction and data and data.highlight then data.highlight.FillColor = COLORS.Red data.highlight.OutlineColor = COLORS.Red end end local function attachInteraction(instance) if connections[instance] then return end if isPrompt(instance) then connections[instance] = instance.Triggered:Connect(function(who) if who == player then markInteracted(instance) markInteracted(getTarget(instance)) end end) elseif isClickDetector(instance) then connections[instance] = instance.MouseClick:Connect(function(who) if who == player then markInteracted(instance) markInteracted(getTarget(instance)) end end) end end local function createVisuals(instance) local target = getTarget(instance) if not target or not target.Parent then return end local adorneePart if target:IsA("BasePart") then adorneePart = target elseif target:IsA("Model") or target:IsA("Tool") then adorneePart = target:FindFirstChildWhichIsA("BasePart", true) else return end if not adorneePart then return end local data = tracked[instance] if not data then data = {} tracked[instance] = data end local color = targetColor(instance) if OPTIONS.ShowHighlights then if not data.highlight or not data.highlight.Parent then local highlight = Instance.new("Highlight") highlight.Name = "ClientESPHighlight" highlight:SetAttribute("CreatedByESP", true) highlight.Adornee = target highlight.Parent = gui data.highlight = highlight end data.highlight.FillColor = color data.highlight.OutlineColor = color data.highlight.DepthMode = OPTIONS.ThroughWalls and Enum.HighlightDepthMode.AlwaysOnTop or Enum.HighlightDepthMode.Occluded data.highlight.Enabled = true elseif data.highlight then data.highlight:Destroy() data.highlight = nil end if OPTIONS.ShowLabels or OPTIONS.ShowDistance then if not data.billboard or not data.billboard.Parent then local billboard = Instance.new("BillboardGui") billboard.Name = "ClientESPLabel" billboard:SetAttribute("CreatedByESP", true) billboard.Size = UDim2.fromOffset(190, 40) billboard.StudsOffset = Vector3.new(0, 2.5, 0) billboard.Adornee = adorneePart billboard.Parent = gui local label = Instance.new("TextLabel") label.Name = "Label" label.Size = UDim2.fromScale(1, 1) label.BackgroundTransparency = 1 label.TextColor3 = color label.TextStrokeTransparency = 0.25 label.Font = Enum.Font.GothamBold label.TextSize = 12 label.Parent = billboard data.billboard = billboard data.label = label end local text = "" if OPTIONS.ShowLabels then text = target.Name end if OPTIONS.ShowDistance then local character = player.Character local root = character and character:FindFirstChild("HumanoidRootPart") if root then local distance = math.floor( (root.Position - adorneePart.Position).Magnitude ) if text ~= "" then text ..= "\n" end text ..= distance .. " studs" end end data.label.Text = text data.label.TextColor3 = color data.billboard.AlwaysOnTop = OPTIONS.ThroughWalls elseif data.billboard then data.billboard:Destroy() data.billboard = nil data.label = nil end end local function hasTargetTypeEnabled() return OPTIONS.ProximityPrompts or OPTIONS.ClickDetectors or OPTIONS.TaggedObjects or OPTIONS.Collectibles or OPTIONS.Tools or OPTIONS.UnanchoredParts end --// WAYPOINTS local waypoints = {} local waypointCounter = 0 local waypointListFrame local refreshWaypointList local waypointFolder = Instance.new("Folder") waypointFolder.Name = "ClientWaypoints" waypointFolder.Parent = Workspace local function getRoot() local character = player.Character return character and character:FindFirstChild("HumanoidRootPart") end local ownedAttachments = setmetatable({}, {__mode = "k"}) local function getRootAttachment(root) local attachment = root:FindFirstChild("ClientESPWaypointRootAttachment") if not attachment then attachment = Instance.new("Attachment") attachment.Name = "ClientESPWaypointRootAttachment" attachment.Parent = root ownedAttachments[attachment] = true end return attachment end --// TELEPORT CORE local lastTeleportOrigin local function teleportTo(position, label, heightOffset) local root = getRoot() if not root then status.Text = "No character to teleport" return end lastTeleportOrigin = root.CFrame local rotation = root.CFrame - root.CFrame.Position root.CFrame = CFrame.new(position + Vector3.new(0, heightOffset or 3, 0)) * rotation root.AssemblyLinearVelocity = Vector3.zero root.AssemblyAngularVelocity = Vector3.zero status.Text = "Teleported to " .. tostring(label) end local function teleportBack() local root = getRoot() if not root or not lastTeleportOrigin then status.Text = "No previous position saved" return end local current = root.CFrame root.CFrame = lastTeleportOrigin lastTeleportOrigin = current root.AssemblyLinearVelocity = Vector3.zero root.AssemblyAngularVelocity = Vector3.zero status.Text = "Returned to previous position" end local function updateWaypoint(wp, isNearest) local root = getRoot() local show = OPTIONS.ShowWaypoints local distance if root then distance = math.floor((root.Position - wp.position).Magnitude) end wp.billboard.Enabled = show local text = wp.name if distance then text ..= "\n" .. distance .. " studs" end wp.label.Text = text wp.label.TextColor3 = wp.color wp.label.TextSize = isNearest and 15 or 12 wp.beam.Color = ColorSequence.new(wp.color) local lineOn = show and OPTIONS.WaypointLines and root ~= nil wp.beam.Enabled = lineOn if lineOn then wp.beam.Attachment1 = getRootAttachment(root) end if wp.distanceLabel and wp.distanceLabel.Parent then wp.distanceLabel.Text = distance and (distance .. " st") or "--" end end local function updateAllWaypoints() local root = getRoot() local nearest local nearestDistance if root then for _, wp in ipairs(waypoints) do local d = (root.Position - wp.position).Magnitude if not nearestDistance or d < nearestDistance then nearest = wp nearestDistance = d end end end for _, wp in ipairs(waypoints) do updateWaypoint(wp, wp == nearest) end end local function removeWaypoint(wp) local index = table.find(waypoints, wp) if index then table.remove(waypoints, index) end if wp.part then wp.part:Destroy() end if wp.billboard then wp.billboard:Destroy() end refreshWaypointList() end local function clearWaypoints() for i = #waypoints, 1, -1 do local wp = table.remove(waypoints, i) if wp.part then wp.part:Destroy() end if wp.billboard then wp.billboard:Destroy() end end refreshWaypointList() end local function addWaypoint(customName, customPosition, customColorName) if #waypoints >= MAX_WAYPOINTS then status.Text = "Waypoint limit reached (" .. MAX_WAYPOINTS .. ")" return end local position = customPosition if not position then local root = getRoot() if not root then status.Text = "No character found for waypoint" return end position = root.Position end waypointCounter += 1 local colorIdx = table.find(colorNames, customColorName or "Yellow") or 4 local wp = { name = customName or ("Waypoint " .. waypointCounter), position = position, colorIndex = colorIdx, color = COLORS[colorNames[colorIdx]], } local part = Instance.new("Part") part.Name = "WaypointMarker" part.Anchored = true part.CanCollide = false part.CanQuery = false part.CanTouch = false part.Transparency = 1 part.Size = Vector3.new(1, 1, 1) part.Position = wp.position part.Parent = waypointFolder wp.part = part local marker = Instance.new("Attachment") marker.Parent = part local beam = Instance.new("Beam") beam.Attachment0 = marker beam.Width0 = 0.15 beam.Width1 = 0.15 beam.FaceCamera = true beam.LightEmission = 1 beam.Color = ColorSequence.new(wp.color) beam.Transparency = NumberSequence.new(0.3) beam.Enabled = false beam.Parent = part wp.beam = beam local billboard = Instance.new("BillboardGui") billboard.Name = "ClientWaypointLabel" billboard.Size = UDim2.fromOffset(150, 40) billboard.StudsOffset = Vector3.new(0, 2, 0) billboard.AlwaysOnTop = true billboard.Adornee = part billboard.Enabled = OPTIONS.ShowWaypoints billboard.Parent = gui wp.billboard = billboard local label = Instance.new("TextLabel") label.Size = UDim2.fromScale(1, 1) label.BackgroundTransparency = 1 label.TextColor3 = wp.color label.TextStrokeTransparency = 0.25 label.Font = Enum.Font.GothamBold label.TextSize = 12 label.Parent = billboard wp.label = label table.insert(waypoints, wp) updateWaypoint(wp) refreshWaypointList() status.Text = "Saved " .. wp.name end refreshWaypointList = function() if not waypointListFrame then return end for _, child in ipairs(waypointListFrame:GetChildren()) do if child:IsA("Frame") then child:Destroy() end end for i, wp in ipairs(waypoints) do local row = Instance.new("Frame") row.Size = UDim2.new(1, -4, 0, 28) row.BackgroundColor3 = Color3.fromRGB(34, 34, 46) row.BorderSizePixel = 0 row.LayoutOrder = i row.Parent = waypointListFrame Instance.new("UICorner", row).CornerRadius = UDim.new(0, 5) local nameBox = Instance.new("TextBox") nameBox.Size = UDim2.new(1, -154, 0, 22) nameBox.Position = UDim2.fromOffset(4, 3) nameBox.BackgroundColor3 = Color3.fromRGB(47, 47, 62) nameBox.Text = wp.name nameBox.PlaceholderText = "Waypoint name" nameBox.TextColor3 = Color3.fromRGB(230, 230, 245) nameBox.PlaceholderColor3 = Color3.fromRGB(140, 140, 160) nameBox.Font = Enum.Font.Gotham nameBox.TextSize = 12 nameBox.TextXAlignment = Enum.TextXAlignment.Left nameBox.ClearTextOnFocus = false nameBox.ClipsDescendants = true nameBox.Parent = row Instance.new("UICorner", nameBox).CornerRadius = UDim.new(0, 4) local namePadding = Instance.new("UIPadding") namePadding.PaddingLeft = UDim.new(0, 6) namePadding.Parent = nameBox nameBox.FocusLost:Connect(function() local newName = nameBox.Text:match("^%s*(.-)%s*$"):sub(1, 24) if newName == "" then nameBox.Text = wp.name return end wp.name = newName nameBox.Text = newName updateWaypoint(wp) status.Text = "Renamed waypoint to " .. newName end) local delete = Instance.new("TextButton") delete.Size = UDim2.fromOffset(28, 22) delete.Position = UDim2.new(1, -32, 0, 3) delete.BackgroundColor3 = Color3.fromRGB(145, 45, 50) delete.Text = "X" delete.TextColor3 = Color3.new(1, 1, 1) delete.Font = Enum.Font.GothamBold delete.TextSize = 12 delete.Parent = row Instance.new("UICorner", delete).CornerRadius = UDim.new(0, 4) delete.Activated:Connect(function() removeWaypoint(wp) end) local colorBtn = Instance.new("TextButton") colorBtn.Size = UDim2.fromOffset(22, 22) colorBtn.Position = UDim2.new(1, -58, 0, 3) colorBtn.BackgroundColor3 = wp.color colorBtn.Text = "" colorBtn.Parent = row Instance.new("UICorner", colorBtn).CornerRadius = UDim.new(0, 4) colorBtn.Activated:Connect(function() wp.colorIndex = wp.colorIndex % #colorNames + 1 wp.color = COLORS[colorNames[wp.colorIndex]] colorBtn.BackgroundColor3 = wp.color updateWaypoint(wp) end) local distanceLabel = Instance.new("TextLabel") distanceLabel.Size = UDim2.fromOffset(52, 22) distanceLabel.Position = UDim2.new(1, -146, 0, 3) distanceLabel.BackgroundTransparency = 1 distanceLabel.Text = "--" distanceLabel.TextColor3 = Color3.fromRGB(165, 165, 180) distanceLabel.Font = Enum.Font.Gotham distanceLabel.TextSize = 11 distanceLabel.TextXAlignment = Enum.TextXAlignment.Right distanceLabel.Parent = row wp.distanceLabel = distanceLabel local tpButton = Instance.new("TextButton") tpButton.Size = UDim2.fromOffset(28, 22) tpButton.Position = UDim2.new(1, -90, 0, 3) tpButton.BackgroundColor3 = Color3.fromRGB(45, 95, 115) tpButton.Text = "TP" tpButton.TextColor3 = Color3.new(1, 1, 1) tpButton.Font = Enum.Font.GothamBold tpButton.TextSize = 11 tpButton.Parent = row Instance.new("UICorner", tpButton).CornerRadius = UDim.new(0, 4) tpButton.Activated:Connect(function() teleportTo(wp.position, wp.name, 0) end) end updateAllWaypoints() end --// Auto waypoint where you die local deathConnection local function hookCharacter(character) local humanoid = character:WaitForChild("Humanoid", 10) local root = character:WaitForChild("HumanoidRootPart", 10) if not humanoid or not root then return end if deathConnection then deathConnection:Disconnect() end deathConnection = humanoid.Died:Connect(function() if running and OPTIONS.AutoDeathWaypoint then addWaypoint("Death", root.Position, "Red") end end) end local characterConnection = player.CharacterAdded:Connect(function(character) task.spawn(hookCharacter, character) end) if player.Character then task.spawn(hookCharacter, player.Character) end task.spawn(function() while running do task.wait(0.25) if running then updateAllWaypoints() end end end) --// PLAYER ESP local playerTracked = {} local function removePlayerVisuals(plr) local data = playerTracked[plr] if not data then return end if data.highlight then data.highlight:Destroy() end if data.billboard then data.billboard:Destroy() end playerTracked[plr] = nil end local function getPlayerName(plr) if OPTIONS.PlayerDisplayNames then return plr.DisplayName end return plr.Name end local function updatePlayerESP() if not running then return end if not OPTIONS.PlayerESP then for plr in pairs(playerTracked) do removePlayerVisuals(plr) end return end local localRoot = getRoot() local color = COLORS[colorNames[colorIndex]] local seen = {} for _, plr in ipairs(Players:GetPlayers()) do if plr ~= player then local character = plr.Character local root = character and character:FindFirstChild("HumanoidRootPart") local head = character and character:FindFirstChild("Head") local adornee = head or root if character and adornee then seen[plr] = true local data = playerTracked[plr] if not data then data = {} playerTracked[plr] = data end if OPTIONS.ShowHighlights then if not data.highlight or not data.highlight.Parent or data.highlight.Adornee ~= character then if data.highlight then data.highlight:Destroy() end local highlight = Instance.new("Highlight") highlight.Name = "ClientPlayerHighlight" highlight.Adornee = character highlight.Parent = gui data.highlight = highlight end data.highlight.FillColor = color data.highlight.OutlineColor = color data.highlight.DepthMode = OPTIONS.ThroughWalls and Enum.HighlightDepthMode.AlwaysOnTop or Enum.HighlightDepthMode.Occluded data.highlight.Enabled = true elseif data.highlight then data.highlight:Destroy() data.highlight = nil end if OPTIONS.ShowLabels or OPTIONS.ShowDistance then if not data.billboard or not data.billboard.Parent or data.billboard.Adornee ~= adornee then if data.billboard then data.billboard:Destroy() end local billboard = Instance.new("BillboardGui") billboard.Name = "ClientPlayerLabel" billboard.Size = UDim2.fromOffset(190, 40) billboard.StudsOffset = Vector3.new(0, 2.5, 0) billboard.Adornee = adornee billboard.Parent = gui local label = Instance.new("TextLabel") label.Name = "Label" label.Size = UDim2.fromScale(1, 1) label.BackgroundTransparency = 1 label.TextStrokeTransparency = 0.25 label.Font = Enum.Font.GothamBold label.TextSize = 12 label.Parent = billboard data.billboard = billboard data.label = label end local text = "" if OPTIONS.ShowLabels then text = getPlayerName(plr) end if OPTIONS.ShowDistance and localRoot then local distance = math.floor( (localRoot.Position - adornee.Position).Magnitude ) if text ~= "" then text ..= "\n" end text ..= distance .. " studs" end data.label.Text = text data.label.TextColor3 = color data.billboard.AlwaysOnTop = OPTIONS.ThroughWalls elseif data.billboard then data.billboard:Destroy() data.billboard = nil data.label = nil end end end end for plr in pairs(playerTracked) do if not seen[plr] then removePlayerVisuals(plr) end end end task.spawn(function() while running do task.wait(PLAYER_UPDATE_INTERVAL) if running and OPTIONS.PlayerESP then updatePlayerESP() end end end) --// PROXIMITY TRIGGER ESP --// Finds things that react when you get close: proximity prompts, --// touch triggers (parts with a TouchTransmitter) and seats. --// Green = you are inside its activation range, Yellow = nearby. local PROX_RANGES = {25, 50, 100, 250, 500, math.huge} local proxRangeIndex = 3 local MAX_PROX_RENDER = 25 local TOUCH_NEAR = 10 local proxCandidates = {} local proxConnections = {} local proxVisuals = {} local proxDiscoveryActive = false local proxNearest local SENSOR_WORDS = { "trigger", "sensor", "detector", "zone", "region", "hitbox", "plate", "pad", "switch", "button", } local function looksLikeSensor(name) name = name:lower() for _, word in ipairs(SENSOR_WORDS) do if name:find(word, 1, true) then return true end end return false end local function findItemInside(zone, excludeList) local params = OverlapParams.new() params.FilterType = Enum.RaycastFilterType.Exclude params.MaxParts = 50 local filter = table.clone(excludeList) table.insert(filter, zone) params.FilterDescendantsInstances = filter local ok, parts = pcall(function() return Workspace:GetPartsInPart(zone, params) end) if not ok then return nil end for _, part in ipairs(parts) do if not part.Anchored then return part.Name end end return nil end local function classifyProx(instance) if instance:IsA("ProximityPrompt") then return "Prompt" end if instance:IsA("TouchTransmitter") then return "Touch" end if instance:IsA("Seat") or instance:IsA("VehicleSeat") then return "Seat" end return nil end local function considerProx(instance) local kind = classifyProx(instance) if kind then proxCandidates[instance] = kind end if instance:IsA("TouchTransmitter") then local part = instance.Parent if part and part:IsA("BasePart") then proxCandidates[part] = proxCandidates[part] or "Item" end elseif instance:IsA("BasePart") and looksLikeSensor(instance.Name) then proxCandidates[instance] = proxCandidates[instance] or "Item" end end local function startProxDiscovery() if proxDiscoveryActive then return end proxDiscoveryActive = true proxConnections.added = Workspace.DescendantAdded:Connect(considerProx) proxConnections.removing = Workspace.DescendantRemoving:Connect(function(instance) proxCandidates[instance] = nil end) task.spawn(function() for index, instance in ipairs(Workspace:GetDescendants()) do if not running or not proxDiscoveryActive then return end considerProx(instance) if index % 1500 == 0 then task.wait() end end end) end local function removeProxVisuals(instance) local data = proxVisuals[instance] if not data then return end if data.highlight then data.highlight:Destroy() end if data.billboard then data.billboard:Destroy() end proxVisuals[instance] = nil end local function clearProxVisuals() for instance in pairs(proxVisuals) do removeProxVisuals(instance) end end local function stopProxDiscovery() proxDiscoveryActive = false for _, connection in pairs(proxConnections) do connection:Disconnect() end table.clear(proxConnections) table.clear(proxCandidates) end local function getProxInfo(instance, kind) if kind == "Item" then if not instance:IsA("BasePart") or isPlayerCharacterPart(instance) then return nil end local hasTouch = instance:FindFirstChildWhichIsA("TouchTransmitter") ~= nil local sensorNamed = looksLikeSensor(instance.Name) local solid = instance.CanCollide local valid = (hasTouch and (not solid or sensorNamed)) or (sensorNamed and not solid) if not valid then return nil end return { instance = instance, kind = kind, part = instance, target = instance, position = instance.Position, reach = TOUCH_NEAR + instance.Size.Magnitude / 2, name = instance.Name, } end local holder = instance.Parent if not holder then return nil end local part local highlightTarget local position if holder:IsA("Attachment") then local parentPart = holder.Parent if parentPart and parentPart:IsA("BasePart") then part = parentPart highlightTarget = parentPart position = holder.WorldPosition end elseif holder:IsA("BasePart") then part = holder highlightTarget = holder position = holder.Position elseif holder:IsA("Model") then part = holder.PrimaryPart or holder:FindFirstChildWhichIsA("BasePart", true) highlightTarget = holder position = holder:GetPivot().Position end if not part or not position then return nil end if kind == "Prompt" then if not instance.Enabled then return nil end return { instance = instance, kind = kind, part = part, target = highlightTarget, position = position, reach = instance.MaxActivationDistance, name = instance.ActionText ~= "" and instance.ActionText or holder.Name, } end if isPlayerCharacterPart(part) then return nil end if kind == "Touch" and not part.CanTouch then return nil end if kind == "Seat" and instance.Disabled then return nil end return { instance = instance, kind = kind, part = part, target = highlightTarget, position = position, reach = TOUCH_NEAR + part.Size.Magnitude / 2, name = part.Name, } end local function updateProximityESP() if not running then return end local anyEnabled = OPTIONS.ProxPrompts or OPTIONS.ProxTouch or OPTIONS.ProxSeats or OPTIONS.ProxItems if not anyEnabled then proxNearest = nil clearProxVisuals() stopProxDiscovery() return end startProxDiscovery() local root = getRoot() if not root then proxNearest = nil clearProxVisuals() return end refreshPlayerCharacters() local maxRange = PROX_RANGES[proxRangeIndex] local list = {} for instance, kind in pairs(proxCandidates) do if not instance.Parent then proxCandidates[instance] = nil elseif (kind == "Prompt" and OPTIONS.ProxPrompts) or (kind == "Touch" and OPTIONS.ProxTouch) or (kind == "Seat" and OPTIONS.ProxSeats) or (kind == "Item" and OPTIONS.ProxItems) then local info = getProxInfo(instance, kind) if info then local distance = (root.Position - info.position).Magnitude if distance <= maxRange then info.distance = distance table.insert(list, info) end end end end table.sort(list, function(a, b) return a.distance < b.distance end) proxNearest = list[1] local excludeList = {} for character in pairs(playerCharacters) do table.insert(excludeList, character) end local keep = {} for index = 1, math.min(#list, MAX_PROX_RENDER) do local info = list[index] local instance = info.instance keep[instance] = true local inRange if info.kind == "Prompt" then inRange = info.distance <= info.reach else inRange = info.distance - info.part.Size.Magnitude / 2 <= TOUCH_NEAR end local itemName if info.kind == "Item" then itemName = findItemInside(info.part, excludeList) end local color if info.kind == "Item" then color = itemName and COLORS.Red or COLORS.Purple else color = inRange and COLORS.Green or COLORS.Yellow end local data = proxVisuals[instance] if not data then data = {} proxVisuals[instance] = data end if not data.highlight or not data.highlight.Parent or data.highlight.Adornee ~= info.target then if data.highlight then data.highlight:Destroy() end local highlight = Instance.new("Highlight") highlight.Name = "ClientProximityHighlight" highlight.Adornee = info.target highlight.Parent = gui data.highlight = highlight end data.highlight.FillColor = color data.highlight.OutlineColor = color data.highlight.DepthMode = OPTIONS.ThroughWalls and Enum.HighlightDepthMode.AlwaysOnTop or Enum.HighlightDepthMode.Occluded data.highlight.Enabled = true if not data.billboard or not data.billboard.Parent or data.billboard.Adornee ~= info.part then if data.billboard then data.billboard:Destroy() end local billboard = Instance.new("BillboardGui") billboard.Name = "ClientProximityLabel" billboard.Size = UDim2.fromOffset(200, 40) billboard.StudsOffset = Vector3.new(0, 3, 0) billboard.Adornee = info.part billboard.Parent = gui local label = Instance.new("TextLabel") label.Name = "Label" label.Size = UDim2.fromScale(1, 1) label.BackgroundTransparency = 1 label.TextStrokeTransparency = 0.25 label.Font = Enum.Font.GothamBold label.TextSize = 12 label.Parent = billboard data.billboard = billboard data.label = label end local kindText = info.kind == "Prompt" and "PROMPT" or info.kind == "Touch" and "TOUCH" or info.kind == "Item" and "ITEM TRIGGER" or "SEAT" local suffix = "" if info.kind == "Item" then if itemName then suffix = " - ITEM INSIDE: " .. itemName end elseif inRange then suffix = " - IN RANGE" end data.label.Text = string.format( "[%s] %s\n%d studs%s", kindText, info.name, math.floor(info.distance), suffix ) data.label.TextColor3 = color data.billboard.AlwaysOnTop = OPTIONS.ThroughWalls end for instance in pairs(proxVisuals) do if not keep[instance] then removeProxVisuals(instance) end end end task.spawn(function() while running do task.wait(PROX_UPDATE_INTERVAL) if running and (OPTIONS.ProxPrompts or OPTIONS.ProxTouch or OPTIONS.ProxSeats or OPTIONS.ProxItems) then updateProximityESP() end end end) --// TELEPORT TO PLAYER / CLICK TELEPORT local teleportListFrame local function refreshPlayerTeleportList(leavingPlayer) if not teleportListFrame then return end for _, child in ipairs(teleportListFrame:GetChildren()) do if child:IsA("Frame") then child:Destroy() end end local order = 0 for _, plr in ipairs(Players:GetPlayers()) do if plr ~= player and plr ~= leavingPlayer then order += 1 local row = Instance.new("Frame") row.Size = UDim2.new(1, -4, 0, 28) row.BackgroundColor3 = Color3.fromRGB(34, 34, 46) row.BorderSizePixel = 0 row.LayoutOrder = order row.Parent = teleportListFrame Instance.new("UICorner", row).CornerRadius = UDim.new(0, 5) local nameLabel = Instance.new("TextLabel") nameLabel.Size = UDim2.new(1, -52, 1, 0) nameLabel.Position = UDim2.fromOffset(8, 0) nameLabel.BackgroundTransparency = 1 nameLabel.Text = getPlayerName(plr) nameLabel.TextColor3 = Color3.fromRGB(230, 230, 245) nameLabel.Font = Enum.Font.Gotham nameLabel.TextSize = 12 nameLabel.TextXAlignment = Enum.TextXAlignment.Left nameLabel.TextTruncate = Enum.TextTruncate.AtEnd nameLabel.Parent = row local tpButton = Instance.new("TextButton") tpButton.Size = UDim2.fromOffset(40, 22) tpButton.Position = UDim2.new(1, -44, 0, 3) tpButton.BackgroundColor3 = Color3.fromRGB(45, 95, 115) tpButton.Text = "TP" tpButton.TextColor3 = Color3.new(1, 1, 1) tpButton.Font = Enum.Font.GothamBold tpButton.TextSize = 11 tpButton.Parent = row Instance.new("UICorner", tpButton).CornerRadius = UDim.new(0, 4) tpButton.Activated:Connect(function() local character = plr.Character local targetRoot = character and character:FindFirstChild("HumanoidRootPart") if targetRoot then teleportTo( targetRoot.Position + targetRoot.CFrame.LookVector * -4, getPlayerName(plr) ) else status.Text = getPlayerName(plr) .. " has no character" end end) end end end local playerAddedConnection = Players.PlayerAdded:Connect(function() refreshPlayerTeleportList() end) local playerRemovingConnection = Players.PlayerRemoving:Connect(function(leaving) refreshPlayerTeleportList(leaving) end) local clickTeleportConnection = UserInputService.InputBegan:Connect(function(input, processed) if processed or not OPTIONS.ClickTeleport then return end if input.UserInputType ~= Enum.UserInputType.MouseButton1 then return end if not UserInputService:IsKeyDown(Enum.KeyCode.LeftControl) then return end local atMouse = playerGui:GetGuiObjectsAtPosition(UserInputService:GetMouseLocation().X, UserInputService:GetMouseLocation().Y) for _, object in ipairs(atMouse) do if object:IsDescendantOf(gui) then return end end local camera = Workspace.CurrentCamera if not camera then return end local mouse = UserInputService:GetMouseLocation() local ray = camera:ViewportPointToRay(mouse.X, mouse.Y) local params = RaycastParams.new() params.FilterType = Enum.RaycastFilterType.Exclude params.FilterDescendantsInstances = {player.Character, waypointFolder} local result = Workspace:Raycast(ray.Origin, ray.Direction * 2000, params) if result then teleportTo(result.Position, "clicked point") end end) --// Scan function local function scan() if not running or scanning then return end if not hasTargetTypeEnabled() or not (OPTIONS.ShowHighlights or OPTIONS.ShowLabels or OPTIONS.ShowDistance) then for instance, connection in pairs(connections) do connection:Disconnect() connections[instance] = nil end for instance in pairs(tracked) do removeVisuals(instance) end status.Text = OPTIONS.PlayerESP and "Player ESP active" or "ESP disabled" return end refreshPlayerCharacters() scanning = true local seen = {} local count = 0 for index, instance in ipairs(Workspace:GetDescendants()) do if not running then scanning = false return end if isTarget(instance) then count += 1 if count <= MAX_ESP_TARGETS then seen[instance] = true if OPTIONS.RedAfterInteraction then if isPrompt(instance) or isClickDetector(instance) then attachInteraction(instance) end end createVisuals(instance) end end if index % 1500 == 0 then task.wait() end end for instance in pairs(tracked) do if not seen[instance] or not instance.Parent then removeVisuals(instance) end end for instance, connection in pairs(connections) do if not instance.Parent or not OPTIONS.RedAfterInteraction then connection:Disconnect() connections[instance] = nil end end scanning = false status.Text = string.format("ESP: %d visible / %d matches | next scan %ds", math.min(count, MAX_ESP_TARGETS), count, SCAN_INTERVAL) end local function requestScan() if not running or scanQueued then return end scanQueued = true task.delay(0.2, function() scanQueued = false if running then scan() end end) end --// Toggle creation local toggleButtons = {} local toggleSetters = {} local function toggle(label, key, callback, noScan) local button = makeButton(label .. ": OFF") toggleButtons[key] = button local function update() local enabled = OPTIONS[key] button.Text = label .. ": " .. (enabled and "ON" or "OFF") button.BackgroundColor3 = enabled and Color3.fromRGB(35, 100, 65) or Color3.fromRGB(47, 47, 62) end toggleSetters[key] = function(value) OPTIONS[key] = value if callback then callback(value) end update() end button.Activated:Connect(function() toggleSetters[key](not OPTIONS[key]) if not noScan then requestScan() end end) update() return button end --// Original-style options and controls newTab("esp", "ESP") newTab("players", "Players") newTab("triggers", "Triggers") newTab("waypoints", "Waypts") newTab("teleport", "Teleport") newTab("movement", "Move") newTab("world", "World") newTab("misc", "Misc") setTab("esp") useTab("esp") section("TARGET TYPES") toggle("Proximity Prompts ESP", "ProximityPrompts") toggle("Click Detectors ESP", "ClickDetectors") toggle("Tagged Interactables ESP", "TaggedObjects") toggle("Collectibles ESP", "Collectibles") toggle("Tools ESP", "Tools") toggle("Unanchored Parts ESP", "UnanchoredParts") useTab("players") section("PLAYER ESP (uses visual options)") toggle("Player ESP", "PlayerESP", updatePlayerESP) local nameModeButton = makeButton("Player Name: Username") nameModeButton.Activated:Connect(function() OPTIONS.PlayerDisplayNames = not OPTIONS.PlayerDisplayNames nameModeButton.Text = "Player Name: " .. (OPTIONS.PlayerDisplayNames and "Display Name" or "Username") nameModeButton.BackgroundColor3 = OPTIONS.PlayerDisplayNames and Color3.fromRGB(35, 100, 65) or Color3.fromRGB(47, 47, 62) updatePlayerESP() refreshPlayerTeleportList() end) useTab("esp") section("VISUAL OPTIONS") toggle("Show Highlights", "ShowHighlights") toggle("Show Labels", "ShowLabels") toggle("Show Distance", "ShowDistance") toggle("Through Walls", "ThroughWalls") toggle("Red After Interaction", "RedAfterInteraction") local promptOverrideApplied = false toggle("Override Prompt Visibility", "PromptsEnabled", function(enabled) promptOverrideApplied = true -- Only modify prompts after the user explicitly selects this option. -- Original values are restored when the GUI is destroyed. for index, instance in ipairs(Workspace:GetDescendants()) do if isPrompt(instance) then if promptOriginal[instance] == nil then promptOriginal[instance] = instance.Enabled end instance.Enabled = enabled end if index % 1500 == 0 then task.wait() end end status.Text = enabled and "Prompts enabled locally" or "Prompts disabled locally" end) promptAddedConnection = Workspace.DescendantAdded:Connect(function(instance) if running and isPrompt(instance) and promptOverrideApplied then promptOriginal[instance] = instance.Enabled instance.Enabled = OPTIONS.PromptsEnabled end end) useTab("triggers") section("PROXIMITY TRIGGERS") toggle("Proximity Prompts", "ProxPrompts", updateProximityESP) toggle("Touch Triggers", "ProxTouch", updateProximityESP) toggle("Seats", "ProxSeats", updateProximityESP) toggle("Item Triggers", "ProxItems", updateProximityESP) local function proxRangeText() local range = PROX_RANGES[proxRangeIndex] return "Proximity Range: " .. (range == math.huge and "Any" or (range .. " studs")) end local proxRangeButton = makeButton(proxRangeText()) proxRangeButton.Activated:Connect(function() proxRangeIndex += 1 if proxRangeIndex > #PROX_RANGES then proxRangeIndex = 1 end proxRangeButton.Text = proxRangeText() updateProximityESP() end) local proxLegend = Instance.new("TextLabel") proxLegend.Size = UDim2.new(1, -4, 0, 40) proxLegend.BackgroundTransparency = 1 proxLegend.Text = "Green = inside activation range, Yellow = nearby. Item Triggers: purple = sensor zone that reacts to loose items, red = an item is inside it. Shows the closest 25." proxLegend.TextColor3 = Color3.fromRGB(150, 150, 170) proxLegend.Font = Enum.Font.Gotham proxLegend.TextSize = 10 proxLegend.TextWrapped = true proxLegend.TextXAlignment = Enum.TextXAlignment.Left proxLegend.Parent = uiParent() useTab("waypoints") section("WAYPOINTS") toggle("Show Waypoints", "ShowWaypoints", updateAllWaypoints) toggle("Waypoint Lines", "WaypointLines", updateAllWaypoints) toggle("Auto Death Waypoint", "AutoDeathWaypoint") local addWaypointButton = makeButton( "Add Waypoint Here", Color3.fromRGB(45, 95, 115) ) addWaypointButton.Activated:Connect(function() addWaypoint() end) local clearWaypointsButton = makeButton( "Clear All Waypoints", Color3.fromRGB(105, 75, 35) ) local confirmClear = false clearWaypointsButton.Activated:Connect(function() if #waypoints == 0 then status.Text = "No waypoints to clear" return end if not confirmClear then confirmClear = true clearWaypointsButton.Text = "Click again to confirm" task.delay(3, function() confirmClear = false if clearWaypointsButton.Parent then clearWaypointsButton.Text = "Clear All Waypoints" end end) return end confirmClear = false clearWaypointsButton.Text = "Clear All Waypoints" clearWaypoints() status.Text = "All waypoints cleared" end) waypointListFrame = Instance.new("Frame") waypointListFrame.Name = "WaypointList" waypointListFrame.Size = UDim2.new(1, -4, 0, 0) waypointListFrame.AutomaticSize = Enum.AutomaticSize.Y waypointListFrame.BackgroundTransparency = 1 waypointListFrame.Parent = uiParent() local waypointListLayout = Instance.new("UIListLayout") waypointListLayout.Padding = UDim.new(0, 4) waypointListLayout.SortOrder = Enum.SortOrder.LayoutOrder waypointListLayout.Parent = waypointListFrame useTab("teleport") section("TELEPORT") toggle("Ctrl+Click Teleport", "ClickTeleport") local tpNearestButton = makeButton( "Teleport To Nearest Trigger", Color3.fromRGB(45, 95, 115) ) tpNearestButton.Activated:Connect(function() if proxNearest then teleportTo(proxNearest.position, proxNearest.name) else status.Text = "Turn on a Proximity Trigger option first" end end) local tpBackButton = makeButton( "Teleport Back", Color3.fromRGB(105, 75, 35) ) tpBackButton.Activated:Connect(teleportBack) section("TELEPORT TO PLAYER") teleportListFrame = Instance.new("Frame") teleportListFrame.Name = "PlayerTeleportList" teleportListFrame.Size = UDim2.new(1, -4, 0, 0) teleportListFrame.AutomaticSize = Enum.AutomaticSize.Y teleportListFrame.BackgroundTransparency = 1 teleportListFrame.Parent = uiParent() local teleportListLayout = Instance.new("UIListLayout") teleportListLayout.Padding = UDim.new(0, 4) teleportListLayout.SortOrder = Enum.SortOrder.LayoutOrder teleportListLayout.Parent = teleportListFrame refreshPlayerTeleportList() useTab("esp") section("HIGHLIGHT COLOR") local colorButton = makeButton("Color: Cyan", COLORS.Cyan) colorButton.Activated:Connect(function() colorIndex += 1 if colorIndex > #colorNames then colorIndex = 1 end colorButton.Text = "Color: " .. colorNames[colorIndex] colorButton.BackgroundColor3 = COLORS[colorNames[colorIndex]] requestScan() end) useTab("misc") section("CONTROLS") local scanButton = makeButton( "Scan Now", Color3.fromRGB(50, 80, 135) ) scanButton.Activated:Connect(scan) local clearButton = makeButton( "Clear Interaction History", Color3.fromRGB(105, 75, 35) ) clearButton.Activated:Connect(function() interacted = setmetatable({}, {__mode = "k"}) requestScan() end) local disableButton = makeButton( "Disable All ESP", Color3.fromRGB(110, 65, 65) ) disableButton.Activated:Connect(function() local keys = { "ProximityPrompts", "ClickDetectors", "TaggedObjects", "Collectibles", "Tools", "UnanchoredParts", "ShowHighlights", "ShowLabels", "ShowDistance", "ThroughWalls", "RedAfterInteraction", "ShowWaypoints", "WaypointLines", "AutoDeathWaypoint", "PlayerESP", "ProxPrompts", "ProxTouch", "ProxSeats", "ProxItems", "ClickTeleport", } for _, key in ipairs(keys) do OPTIONS[key] = false end updateAllWaypoints() updatePlayerESP() updateProximityESP() for _, key in ipairs(keys) do local setter = toggleSetters[key] if setter then setter(false) end end requestScan() status.Text = "All ESP disabled" end) local killButton = makeButton( "KILL GUI", Color3.fromRGB(170, 40, 45) ) local function killGUI() if not running then return end running = false for _, connection in pairs(connections) do if connection then connection:Disconnect() end end table.clear(connections) for instance in pairs(tracked) do removeVisuals(instance) end clearProxVisuals() stopProxDiscovery() playerAddedConnection:Disconnect() playerRemovingConnection:Disconnect() clickTeleportConnection:Disconnect() for plr in pairs(playerTracked) do removePlayerVisuals(plr) end clearWaypoints() waypointFolder:Destroy() if deathConnection then deathConnection:Disconnect() end if promptAddedConnection then promptAddedConnection:Disconnect() end for prompt, wasEnabled in pairs(promptOriginal) do if prompt.Parent then prompt.Enabled = wasEnabled end end for attachment in pairs(ownedAttachments) do if attachment.Parent then attachment:Destroy() end end dragConnection:Disconnect() keyConnection:Disconnect() sliderMoveConnection:Disconnect() sliderEndConnection:Disconnect() characterConnection:Disconnect() local root = getRoot() local rootAttachment = root and root:FindFirstChild("ClientESPWaypointRootAttachment") if rootAttachment then rootAttachment:Destroy() end gui:Destroy() if _G.__ClientESPPanelShutdown == killGUI then _G.__ClientESPPanelShutdown = nil end end _G.__ClientESPPanelShutdown = killGUI killButton.Activated:Connect(killGUI) closeButton.Activated:Connect(killGUI) --// Automatically scan once every 5 seconds. --// No continuous RenderStepped scanning. task.spawn(function() while running and gui.Parent do task.wait(SCAN_INTERVAL) if running and gui.Parent then scan() end end end) status.Text = "Ready | ESP off | scan every 5s when enabled"