User.unlisten removes ALL listeners for an event, not just the caller's, which makes it unsafe whenever more than one component listens to the same socket event:
public void listen(String event, Emitter.Listener listener) {
if(socket != null) socket.on(event, listener);
}
public void unlisten(String event) {
if(socket != null) socket.off(event); // socket.off(event) removes EVERY listener for that event
}
socket.io's socket.off(event) with no listener argument clears every handler registered for that event. So when one component tears down and calls unlisten(SCENE_EVENT) (or UPDATE_ROOM, CHAT_MESSAGE, etc.), it also kills any other component's handler for that same event.
Concrete example: SessionScreen listens to UPDATE_ROOM / READY_USER / CHAT_MESSAGE and in onDestroy calls user.unlisten(...) on each. If anything else is also listening on one of those events, it gets silently unhooked too, and stops receiving updates with no obvious cause. UserSceneSocketBridge.detach() has the same broad-unlisten pattern on SCENE_EVENT / UPDATE_USER / ADD_COINS.
The fix is to make unlisten scoped: keep the specific Emitter.Listener reference and call socket.off(event, listener), so each component only removes its own handler.
File: core/src/com/focus/kingdom/network/dto/User.java, listen/unlisten around line 358-368.
User.unlistenremoves ALL listeners for an event, not just the caller's, which makes it unsafe whenever more than one component listens to the same socket event:socket.io's
socket.off(event)with no listener argument clears every handler registered for that event. So when one component tears down and callsunlisten(SCENE_EVENT)(or UPDATE_ROOM, CHAT_MESSAGE, etc.), it also kills any other component's handler for that same event.Concrete example: SessionScreen listens to UPDATE_ROOM / READY_USER / CHAT_MESSAGE and in onDestroy calls
user.unlisten(...)on each. If anything else is also listening on one of those events, it gets silently unhooked too, and stops receiving updates with no obvious cause. UserSceneSocketBridge.detach() has the same broad-unlisten pattern on SCENE_EVENT / UPDATE_USER / ADD_COINS.The fix is to make unlisten scoped: keep the specific Emitter.Listener reference and call
socket.off(event, listener), so each component only removes its own handler.File:
core/src/com/focus/kingdom/network/dto/User.java, listen/unlisten around line 358-368.