VIP Door Teleports User On Top Of Building

I have a pretty basic “VIP” Door, but I’m coming across an issue where the script that checks if you have the gamepass teleports you on top of the building, if you own it. Instead of past it. Then inside of the script, I have an IntValue named “GamePassId” which contains the gamepass idea. Could somebody review my code and suggest how I may fix it?

The Script Should:

  • Check if the player has said gamepass.
  • Do nothing if players do not have said gamepass.
  • Teleport players through the door instead of on the roof.
local function WaitForChild(parent, childName)
	assert(parent, "ERROR: WaitForChild: parent is nil")
	while not parent:FindFirstChild(childName) do parent.ChildAdded:wait() end
	return parent[childName]
end

local GamePassService = game:GetService('MarketplaceService')
local PlayersService = game:GetService('Players')

local VipDoor = script.Parent

local GamePassIdObject = script:WaitForChild( 'GamePassId')

local JustTouched = {}

local function TeleportToOtherSide(character, hitPart)
	local bottomOfDoor = VipDoor.CFrame.p - Vector3.new(0, VipDoor.Size.Y / 2, 0)
	local inFrontOfDoor = bottomOfDoor + VipDoor.CFrame.lookVector * 3
	local behindDoor = bottomOfDoor - VipDoor.CFrame.lookVector * 3
	
	local distanceToFront = (inFrontOfDoor - hitPart.Position).magnitude
	local distanceToBack = (behindDoor - hitPart.Position).magnitude
	if distanceToFront < distanceToBack then
		character:MoveTo(behindDoor)
	else
		character:MoveTo(inFrontOfDoor)
	end
end

local function OnTouched(otherPart)
	if otherPart and otherPart.Parent and otherPart.Parent:FindFirstChild('Humanoid') then
		local player = PlayersService:GetPlayerFromCharacter(otherPart.Parent)
		if player and not JustTouched[player] then
			JustTouched[player] = time()
			if GamePassService:UserOwnsGamePassAsync(player.userId, GamePassIdObject.Value) then
				TeleportToOtherSide(player.Character, otherPart)
			end
		end
	end
end

local function RemoveOldTouches()
	for player, touchTime in pairs(JustTouched) do
		if time() > touchTime + 0.3 then
			JustTouched[player] = nil
		end
	end
end

VipDoor.Touched:connect(OnTouched)

while true do
	RemoveOldTouches()
	wait(1/30)
end
4 Likes

Do the script generate an error in the output ?

1 Like

No, or at least as far as my tests prove it doesn’t produce an error.

1 Like

Have you tried checking the direction of the door’s lookvector? Maybe the door isn’t well built and the lookvector is somewhere pointing up.

1 Like

So, I don’t know if this changes anything. The door is a normal “part” with a script in it, sometimes it teleports on top the building and other times it works normally. But it’s more like 40% success, 60% failure.

Could you add in the TeleportToOtherSide function prints of the bottom,front and behind positions? They shouldn’t be different when the function is executed more times. Do that and test it until you get on top instead of getting in the front/back and then see if the positions are changed. (This is just a little debug)

There’s just the one script I posted in the first post for the entire part. Working on, I believe all sides.

I genuinely don’t pretty much have an idea how to fix it, but it’s 100% some problem at the calculations. One more thing, what if you’d add a little debounce in the touch function? Around 0.5 - 1s and see if it works. I was thinking that it would get teleported past the part and then it gets touched again and somehow the calculations get messed up? I don’t really know, just a thought.

That’s because you’re using MoveTo which takes into account collisions before performing the teleport.

Use PivotTo or SetPrimaryPartCFrame if you don’t want to account for collisions.

I have made some tests and you are right! MoveTo is the problem. Thanks for helping us solve this! :smile: