function DPad.Enable(a)DPadFrame.Visible=true end function DPad.Disable(a)DPadFrame.Visible=false OnInputEnded()end function DPad.Create(n,a)if DPadFrame then DPadFrame:Destroy()DPadFrame=nil end local t=UDim2.new(0,10,1,-230)DPadFrame=Instance.new("\070\114\097\109\101")DPadFrame.Name="\068\080\097\100\070\114\097\109\101"DPadFrame.Active=true DPadFrame.Visible=false DPadFrame.Size=UDim2.new(0,192,0,192)DPadFrame.Position=t DPadFrame.BackgroundTransparency=1 local H=UDim2.new(0,23,0,23)local O=UDim2.new(0,64,0,64)local z=Vector2.new(46,46)local L=Vector2.new(128,128)local N=createArrowLabel("\066\097\099\107\066\117\116\116\111\110",UDim2.new(.5,-32,1,-64),O,Vector2.new(0,0),L)local r=createArrowLabel("\070\111\114\119\097\114\100\066\117\116\116\111\110",UDim2.new(.5,-32,0,0),O,Vector2.new(0,258),L)local A=createArrowLabel("\076\101\102\116\066\117\116\116\111\110",UDim2.new(0,0,.5,-32),O,Vector2.new(129,129),L)local i=createArrowLabel("\082\105\103\104\116\066\117\116\116\111\110",UDim2.new(1,-64,.5,-32),O,Vector2.new(0,129),L)local T=createArrowLabel("\074\117\109\112\066\117\116\116\111\110",UDim2.new(.5,-32,.5,-32),O,Vector2.new(129,0),L)local c=createArrowLabel("\070\111\114\119\097\114\100\076\101\102\116\066\117\116\116\111\110",UDim2.new(0,35,0,35),H,Vector2.new(129,258),z)local U=createArrowLabel("\070\111\114\119\097\114\100\082\105\103\104\116\066\117\116\116\111\110",UDim2.new(1,-55,0,35),H,Vector2.new(176,258),z)c.Visible=false U.Visible=false T.InputBegan:connect(function(a)MasterControl:DoJump()end)local D=Vector3.new(0,0,0)local function G(a)local n=T.AbsoluteSize.x/2 local t=getCenterPosition()local H=Vector2.new(a.x-t.x,a.y-t.y)if H.magnitude>n then local a=ATAN2(H.y,H.x)local n=FLOOR((8*a)/(2*PI)+8.5)%8+1 D=COMPASS_DIR[n]end if not c.Visible and D==COMPASS_DIR[7]then c.Visible=true U.Visible=true end end DPadFrame.InputBegan:connect(function(a)if TouchObject or a.UserInputType~=Enum.UserInputType.Touch then return end MasterControl:AddToPlayerMovement(-D)TouchObject=a G(TouchObject.Position)MasterControl:AddToPlayerMovement(D)end)DPadFrame.InputChanged:connect(function(a)if a==TouchObject then MasterControl:AddToPlayerMovement(-D)G(TouchObject.Position)MasterControl:AddToPlayerMovement(D)MasterControl:SetIsJumping(false)end end)OnInputEnded=function()TouchObject=nil c.Visible=false U.Visible=false MasterControl:AddToPlayerMovement(-D)D=Vector3.new(0,0,0)end DPadFrame.InputEnded:connect(function(a)if a==TouchObject then OnInputEnded()end end)GuiService.MenuOpened:connect(function()if TouchObject then OnInputEnded()end end)DPadFrame.Parent=a end return DPad
--[[ Public API ]]
--
function DPad:Enable()
	DPadFrame.Visible = true
end

function DPad:Disable()
	DPadFrame.Visible = false
	OnInputEnded()
end

function DPad:Create(parentFrame)
	if DPadFrame then
		DPadFrame:Destroy()
		DPadFrame = nil
	end

	local position = UDim2.new(0, 10, 1, -230)
	DPadFrame = Instance.new("Frame")
	DPadFrame.Name = "DPadFrame"
	DPadFrame.Active = true
	DPadFrame.Visible = false
	DPadFrame.Size = UDim2.new(0, 192, 0, 192)
	DPadFrame.Position = position
	DPadFrame.BackgroundTransparency = 1

	local smArrowSize = UDim2.new(0, 23, 0, 23)
	local lgArrowSize = UDim2.new(0, 64, 0, 64)
	local smImgOffset = Vector2.new(46, 46)
	local lgImgOffset = Vector2.new(128, 128)

	local bBtn =
		createArrowLabel("BackButton", UDim2.new(0.5, -32, 1, -64), lgArrowSize, Vector2.new(0, 0), lgImgOffset)
	local fBtn =
		createArrowLabel("ForwardButton", UDim2.new(0.5, -32, 0, 0), lgArrowSize, Vector2.new(0, 258), lgImgOffset)
	local lBtn =
		createArrowLabel("LeftButton", UDim2.new(0, 0, 0.5, -32), lgArrowSize, Vector2.new(129, 129), lgImgOffset)
	local rBtn =
		createArrowLabel("RightButton", UDim2.new(1, -64, 0.5, -32), lgArrowSize, Vector2.new(0, 129), lgImgOffset)
	local jumpBtn =
		createArrowLabel("JumpButton", UDim2.new(0.5, -32, 0.5, -32), lgArrowSize, Vector2.new(129, 0), lgImgOffset)
	local flBtn =
		createArrowLabel("ForwardLeftButton", UDim2.new(0, 35, 0, 35), smArrowSize, Vector2.new(129, 258), smImgOffset)
	local frBtn = createArrowLabel(
		"ForwardRightButton",
		UDim2.new(1, -55, 0, 35),
		smArrowSize,
		Vector2.new(176, 258),
		smImgOffset
	)
	flBtn.Visible = false
	frBtn.Visible = false

	-- input connections
	jumpBtn.InputBegan:connect(function(inputObject)
		MasterControl:DoJump()
	end)

	local movementVector = Vector3.new(0, 0, 0)
	local function normalizeDirection(inputPosition)
		local jumpRadius = jumpBtn.AbsoluteSize.x / 2
		local centerPosition = getCenterPosition()
		local direction = Vector2.new(inputPosition.x - centerPosition.x, inputPosition.y - centerPosition.y)

		if direction.magnitude > jumpRadius then
			local angle = ATAN2(direction.y, direction.x)
			local octant = (FLOOR(8 * angle / (2 * PI) + 8.5) % 8) + 1
			movementVector = COMPASS_DIR[octant]
		end

		if not flBtn.Visible and movementVector == COMPASS_DIR[7] then
			flBtn.Visible = true
			frBtn.Visible = true
		end
	end

	DPadFrame.InputBegan:connect(function(inputObject)
		if TouchObject or inputObject.UserInputType ~= Enum.UserInputType.Touch then
			return
		end

		MasterControl:AddToPlayerMovement(-movementVector)

		TouchObject = inputObject
		normalizeDirection(TouchObject.Position)

		MasterControl:AddToPlayerMovement(movementVector)
	end)

	DPadFrame.InputChanged:connect(function(inputObject)
		if inputObject == TouchObject then
			MasterControl:AddToPlayerMovement(-movementVector)
			normalizeDirection(TouchObject.Position)
			MasterControl:AddToPlayerMovement(movementVector)
			MasterControl:SetIsJumping(false)
		end
	end)

	OnInputEnded = function()
		TouchObject = nil
		flBtn.Visible = false
		frBtn.Visible = false

		MasterControl:AddToPlayerMovement(-movementVector)
		movementVector = Vector3.new(0, 0, 0)
	end

	DPadFrame.InputEnded:connect(function(inputObject)
		if inputObject == TouchObject then
			OnInputEnded()
		end
	end)

	GuiService.MenuOpened:connect(function()
		if TouchObject then
			OnInputEnded()
		end
	end)

	DPadFrame.Parent = parentFrame
end

return DPad
