Infuriating Logic Issue in code

Hello everyone, I’ve been having a quite frustrating issue with some logic in my code recently, and despite me scripting on roblox for over 4 years, I cannot seem to wrap my head around how to get this code to work.

Basically, I have some code that prevents the player from equipping tools while crouching. The problem is, the player can still somehow always find a way to equip the tool and crouch at the same time.

I am almost certain the solution lies within Equip(), because I tested HandleCrouchRemove() with prints and everything seemed to work fine.

Any help would be greatly appreciated!!!

Logic:

Player equips a tool, and then crouches, the weapon gets removed, but if they stand up it gives the tool back.

Player equips a tool, crouches, equips a second tool, then stands up, it gives them the second tool, as that's the new item.

Player equips a tool, crouches, equips nothing, then stands up, it gives them nothing.

Player equips nothing, crouches, equips tool, then stands up, it gives tool

Player equips tool, crouches, then unequips tool, then re-equips tool, it doesn't give them the tool until they stand up.

Code (stripped)

local PlayerCrouchRemoves = {}

function Equip(Player,CurrentTool,PreviousTool)
	
	-- Logic?

	if CurrentTool ~= nil then
		CurrentTool.Parent = Player.Character
	end

	if PreviousTool ~= nil and PreviousTool.Parent == Player.Character then
		PreviousTool.Parent = Player.Backpack
	end
end

function HandleCrouchRemove(Player,Parameter1)
	
	if Parameter1 == true then
		
		for _,Object in pairs(Player.Character:GetChildren()) do
			if Object:IsA("Tool") then
				
				Object.Parent = Player.Backpack
				PlayerCrouchRemoves[Player] = Object
				
				return
			end
		end
		
		PlayerCrouchRemoves[Player] = true
		
	elseif Parameter1 == false then
		
		if (PlayerCrouchRemoves[Player] ~= true and PlayerCrouchRemoves[Player] ~= nil) then
			PlayerCrouchRemoves[Player].Parent = Player.Character
		end
		
		PlayerCrouchRemoves[Player] = nil
	end
end

Events.HandleCrouchRemove.OnServerEvent:Connect(HandleCrouchRemove)

i’m pretty confused as to why you’re allowing the player to equip tools while crouching

maybe you just didn’t explain that tools should get Disabled when crouching, not unequipped (i would think this is a better design choice)

Player equips a tool, and then crouches -> the tool gets disabled; Player stands up -> the tool gets enabled

Player equips a tool, and then crouches -> the tool gets disabled; Player equips a new tool -> new tool gets disabled; Player stands up -> the new tool gets enabled

Player equips a tool, and then crouches -> the tool gets disabled; Player equips nothing -> nothing gets disabled; Player stands up -> nothing gets enabled

Player equips nothing, and then crouches -> nothing gets disabled; Player equips a tool -> the tool gets disabled; Player stands up -> the tool gets enabled

Player equips a tool, and then crouches -> the tool gets disabled; Player unequips the tool -> nothing gets disabled; Player equips a tool -> the tool gets disabled; Player stands up -> the tool gets enabled

so based off this, you need a way to equip/unequip tools, disable/enable tools, and crouch/stand up

don’t make a function like HandleCrouchRemove. just disable the tools using the crouch function, and enable the tools using the stand up function

so if we rewrote the ‘logic’ using functions

Equip(Axe); Crouch() -> DisableCurrentTool(); StandUp() -> EnableCurrentTool()

Equip(Axe); Crouch() -> DisableCurrentTool(); Equip(Sword) -> DisableCurrentTool(); StandUp() -> EnableCurrentTool()

Equip(Axe); Crouch() -> DisableCurrentTool(); Equip(nil) or UnequipCurrentTool() -> DisableCurrentTool(); StandUp() -> EnableCurrentTool()

Equip(nil) or UnequipCurrentTool(); Crouch() -> DisableCurrentTool(); Equip(Axe) -> DisableCurrentTool(); StandUp() -> EnableCurrentTool()

Equip(Axe); Crouch() -> DisableCurrentTool(); Equip(nil) or UnequipCurrentTool() -> DisableCurrentTool(); Equip(Axe) -> DisableCurrentTool(); StandUp() -> EnableCurrentTool()

here you can see that only crouching or equipping items may lead to DisableCurrentTool() being called.

if you equip an item, you should check if you’re crouching and if you have a tool equipped → DisableCurrentTool()

if you stand up, you should check if you have a tool and if it’s disabled → EnableCurrentTool()

if i’m understanding this logic correctly, i am almost certain the solution involves you differentiating between unequipped and disabled tools (or you just aren’t tracking your newly equipped tool; refer to the very first sentence)

Greetings, Mythamanx.

The simplest way to achieve this would be to make your own hotbar system. If you don’t want to, then you can just remove the tool by parenting it’s Handle to something like nil and sending data to the client to stop all animations if there are any playing.

In a more organized way:

  • Player equips tool while not being crouched, tool equips.
  • Player equips tool then crouches, the handle of the tool is parented to nil and animations are stopped.
  • Player changes tool while being crouched, the tool equips fine but handle is parented to nil and animations are stopped.
  • Player gets up from crouching state, handle is parented to the tool again and animations are played again.

You can detect crouching state by using an attribute or a boolean value and just using a GetAttributeChangedSignal or GetPropertyChangedSignal (respectively) to see if the player is crouched or not.

Hope this helped.