ContextActionService buttons not appearing on iPad device

I have a tester on an Apple iPad device. When the user picks up a railgun or sniper rifle, a Z button appears on their screen. When they press the Z button, the zoom scope show up as it’s supposed to. However, the Z+ and Z- buttons don’t show up. I have set the scope mask Z-index to -16384 along with its containing frame and the problem persists. Below are screenshots from both an iPad and a Kindle Fire.

First, the iPad screenshots.

Now the Amazon Kindle Fire screenshot.

Now I had the tester type /console into the chat to pull up the developer console to see if there was any errors. This is what they are seeing:

The messages look to me like they are some kind of informational messages about thread activity. Beyond that I have no idea.

Now, I have removed the sniper scope mask and had the tester try it again. The buttons appear and disappear like they are supposed to when entering and exiting zoom mode. See the screenshot below.

So the Z+ and Z- button are there as well as the Z and R buttons. As I mentioned before, I set the Z-Index of both the frame and the graphic overlay to -16384. So does anyone have any idea why the buttons are being covered up on an iPad?

EDIT 9/21/2022 @ 1605 PDT

It might help if I include the zoom enable code. This code executes on the client in a client only module script.

-- Turns on the gun scope zoom.  Sets up the zoom and
-- all keybindings, button, touch, and mouse events.
local function zoomIn(localPlayer, toolData, toolInstance)
	localPlayer.CameraMode = Enum.CameraMode.LockFirstPerson
	workspace.CurrentCamera.FieldOfView = toolData.zoom.fieldOfView
	localPlayer.Character.Humanoid.CameraOffset =, 0, 4)
	toolData.zoom.current = toolData.zoom.fieldOfView
	-- Hide the weapon from view

	-- There can be any number of different inputs, but the
	-- code to handle them all is the same.

	-- This will be used by touch screens to set
	-- button locations for ContextActionService.
	local screenSize = workspace.CurrentCamera.ViewportSize

	-- Set keyboard hotkeys and gamepad buttons for variable zoom
	CAS:BindAction("ScopeZoomIn", zoomScope, true, Enum.KeyCode.RightBracket,
	CAS:SetTitle("ScopeZoomIn", "Z+")
	CAS:SetPosition("ScopeZoomIn",, -60, 0, -95))
	CAS:BindAction("ScopeZoomOut", zoomScope, true, Enum.KeyCode.LeftBracket,
	CAS:SetTitle("ScopeZoomOut", "Z-")
	CAS:SetPosition("ScopeZoomOut",, -60, 0, -45))

	-- Use mouse wheel for variable zoom if there's a mouse.
	local mouse = localPlayer:GetMouse()

	if mouse and mouse ~= nil then

		-- Zoom In
		toolData.zoom.mouseWheelForward = mouse.WheelForward:Connect(function()

		-- Zoom Out	
		toolData.zoom.mouseWheelBackward = mouse.WheelBackward:Connect(function()

	-- Touch enabled displays (mostly phones and tablets)
	if UIS.TouchEnabled then
		toolData.zoom.touchPinch = UIS.TouchPinch:Connect(function(position, scale,
			velocity, state, gameProcessedEvent)
			print(scale, velocity, state)


The only possible reason I can think of at this time is maybe when you position it, it might have messed up for different screens?

Maybe the -60 and -45 in the second and fourth parameter is messing it up?

Sorry if this does not help, it is all I can think of at this time.

Maybe only use the first and third parameter to see if that fixes it?

I have thought of that, and I tested it with the device emulator. It shows up correctly when the scope overlay graphic is disabled, which points to a Z-Index issue. But the Z-Index is already at the minimum value allowed for a uint16_t datatype (16-bit integer) which is what the Z-Index is.

I’m beginning to this that this may be an engine bug or something because I’m stumped on this one myself.

Yeah, I’m not too sure myself. I don’t mess with mobile buttons, sorry.

I just did some more testing in the emulator, and it does work correctly in the emulator, but not on the live device. That may point to a bug in the device specific client. I’m surprised that nobody else has stumbled upon this issue.