fix:Change the behavior of reloading the webpage when the receiver exits the room to a more elegant approach

This commit is contained in:
david_bai
2025-08-13 22:53:49 +08:00
parent 12cda8c030
commit 7038e79726
4 changed files with 61 additions and 7 deletions
+21 -5
View File
@@ -51,6 +51,7 @@ const ClipboardApp = () => {
onFileMetadataReceived,
onFileFullyReceived,
handleDownloadFile,
resetReceiverState,
} = useFileTransferHandler({ messages, putMessageInMs });
// Calculate the derived states for unload protection
const isContentPresent = useMemo(() => {
@@ -73,6 +74,7 @@ const ClipboardApp = () => {
setReceiverDirectoryHandle,
getReceiverSaveType,
senderDisconnected,
resetReceiverConnection,
} = useWebRTCConnection({
shareContent,
sendFiles,
@@ -84,11 +86,25 @@ const ClipboardApp = () => {
onFileReceived: onFileFullyReceived,
});
const resetAppState = useCallback(() => {
// This function will reset the state of the application
// For now, it just reloads the page, a more granular state reset can be implemented later.
window.location.reload();
}, []);
const resetAppState = useCallback(async () => {
// Graceful state reset instead of page reload
try {
// Reset file transfer state
resetReceiverState();
// Reset WebRTC connection state
await resetReceiverConnection();
// Reset room input
setRetrieveRoomIdInput("");
console.log("Application state reset successfully");
} catch (error) {
console.error("Error during state reset:", error);
// Fallback to page reload if graceful reset fails
window.location.reload();
}
}, [resetReceiverState, resetReceiverConnection]);
// Initialize Room Manager Hook
const {
+8
View File
@@ -70,6 +70,13 @@ export function useFileTransferHandler({
setRetrievedFileMetas([]);
}, []);
// Reset function specifically for receiver state (for leave room functionality)
const resetReceiverState = useCallback(() => {
setRetrievedContent("");
setRetrievedFiles([]);
setRetrievedFileMetas([]);
}, []);
// Callbacks for useWebRTCConnection
const onStringDataReceived = useCallback((data: string, peerId: string) => {
// console.log(`FileTransferHandler received string from ${peerId}`);
@@ -167,6 +174,7 @@ export function useFileTransferHandler({
removeFileToSend,
clearSentItems,
clearRetrievedItems,
resetReceiverState, // Export the new reset function
// Callbacks to provide to useWebRTCConnection
onStringDataReceived,
onFileMetadataReceived,
+9
View File
@@ -318,6 +318,14 @@ export function useWebRTCConnection({
return receiverFileTransfer?.saveType;
}, [receiverFileTransfer]);
// Reset function for receiver connection (for leave room functionality)
const resetReceiverConnection = useCallback(async () => {
if (receiver) {
await receiver.leaveRoomAndCleanup();
setSenderDisconnected(false);
}
}, [receiver]);
return {
sender, // Exposed for useRoomManager (e.g., sender.isInRoom, sender.joinRoom)
receiver, // Exposed for useRoomManager
@@ -333,5 +341,6 @@ export function useWebRTCConnection({
setReceiverDirectoryHandle,
getReceiverSaveType,
senderDisconnected,
resetReceiverConnection, // Export the new reset function
};
}
+23 -2
View File
@@ -55,8 +55,8 @@ export default class BaseWebRTC {
public onError: CallbackTypes["onError"] | null;
protected iceCandidatesQueue: Map<string, RTCIceCandidateInit[]>;
protected roomId: string | null;
protected peerId: string | undefined | null;
public roomId: string | null;
public peerId: string | undefined | null;
public isInRoom: boolean;
protected isInitiator: boolean; // Flag for the initiator
// Reconnection related
@@ -497,6 +497,27 @@ export default class BaseWebRTC {
}
this.isInRoom = false;
}
// Public method to leave room and cleanup connections while keeping socket alive
public async leaveRoomAndCleanup(): Promise<void> {
// Clean up all peer connections
for (const peerId of Array.from(this.peerConnections.keys())) {
await this.cleanupExistingConnection(peerId);
}
// Reset room-related state but keep socket connected
this.isInRoom = false;
this.roomId = null;
this.isInitiator = false;
this.isPeerDisconnected = false;
this.isSocketDisconnected = false;
this.reconnectionInProgress = false;
this.log(
"log",
"Left room and cleaned up connections, socket remains connected"
);
}
// Abstract method declaration
protected createDataChannel(peerId: string) {
throw new Error("createDataChannel must be implemented by subclass");