chore(code):Add cache room ID feature, no need to manually input room ID

This commit is contained in:
david_bai
2025-10-23 20:47:49 +08:00
parent 0d308515a7
commit 5ca89d71ad
12 changed files with 213 additions and 3 deletions
+1
View File
@@ -202,6 +202,7 @@ const ClipboardApp = () => {
shareMessage={shareMessage}
currentValidatedShareRoomId={shareRoomId}
handleLeaveSenderRoom={handleLeaveSenderRoom}
putMessageInMs={putMessageInMs}
/>
) : (
<RetrieveTabPanel
@@ -1,15 +1,17 @@
import React, { useCallback } from "react";
import React, { useCallback, useEffect, useState } from "react";
import { Input } from "@/components/ui/input";
import { Button } from "@/components/ui/button";
import {
ReadClipboardButton,
WriteClipboardButton,
} from "@/components/common/clipboard_btn";
import Tooltip from "@/components/Tooltip";
import FileListDisplay from "@/components/ClipboardApp/FileListDisplay";
import type { Messages } from "@/types/messages";
import type { FileMeta } from "@/types/webrtc";
import { useFileTransferStore } from "@/stores/fileTransferStore";
import { getCachedId, setCachedId } from "@/lib/roomIdCache";
interface RetrieveTabPanelProps {
messages: Messages;
@@ -60,6 +62,12 @@ export function RetrieveTabPanel({
isReceiverInRoom,
} = useFileTransferStore();
// Cached ID state
const [hasCachedId, setHasCachedId] = useState<boolean>(false);
useEffect(() => {
setHasCachedId(!!getCachedId());
}, []);
const onLocationPick = useCallback(async (): Promise<boolean> => {
if (!messages) return false; // Should not happen if panel is rendered
if (!window.showDirectoryPicker) {
@@ -111,6 +119,46 @@ export function RetrieveTabPanel({
title={messages.text.ClipboardApp.html.readClipboard_dis}
onRead={setRetrieveRoomIdInput}
/>
{/* Save/Use Cached ID Button placed after Paste button */}
<Tooltip
content={
hasCachedId
? messages.text.ClipboardApp.html.useCachedId_tips
: messages.text.ClipboardApp.html.saveId_tips
}
>
<span className="inline-block">
<Button
className="w-full sm:w-auto px-4"
variant="outline"
onClick={() => {
if (hasCachedId) {
const cached = getCachedId();
if (cached) {
setRetrieveRoomIdInput(cached);
}
} else {
const trimmed = retrieveRoomIdInput.trim();
if (trimmed.length >= 8) {
setCachedId(trimmed);
setHasCachedId(true);
putMessageInMs(
messages.text.ClipboardApp.saveId_success,
false
);
}
}
}}
disabled={
!hasCachedId && retrieveRoomIdInput.trim().length < 8
}
>
{hasCachedId
? messages.text.ClipboardApp.html.useCachedId_dis
: messages.text.ClipboardApp.html.saveId_dis}
</Button>
</span>
</Tooltip>
<Input
aria-label="Retrieve Room ID"
value={retrieveRoomIdInput}
@@ -2,6 +2,7 @@ import React, { useState, useEffect, useCallback } from "react";
import dynamic from "next/dynamic";
import { Input } from "@/components/ui/input";
import { Button } from "@/components/ui/button";
import Tooltip from "@/components/Tooltip";
import {
ReadClipboardButton,
WriteClipboardButton,
@@ -13,6 +14,7 @@ import type { Messages } from "@/types/messages";
import type { CustomFile, FileMeta } from "@/types/webrtc";
import { useFileTransferStore } from "@/stores/fileTransferStore";
import { getCachedId, setCachedId } from "@/lib/roomIdCache";
// Dynamically import the RichTextEditor
const RichTextEditor = dynamic(
@@ -39,6 +41,11 @@ interface SendTabPanelProps {
shareMessage: string;
currentValidatedShareRoomId: string;
handleLeaveSenderRoom: () => void; // New prop for leaving room
putMessageInMs: (
message: string,
isShareEnd?: boolean,
displayTimeMs?: number
) => void;
}
export function SendTabPanel({
@@ -53,6 +60,7 @@ export function SendTabPanel({
shareMessage,
currentValidatedShareRoomId,
handleLeaveSenderRoom,
putMessageInMs,
}: SendTabPanelProps) {
// Get the status from the store
const {
@@ -69,12 +77,18 @@ export function SendTabPanel({
);
// State to track ID generation mode (false = will show simple next, true = will show random next)
const [isSimpleIdMode, setIsSimpleIdMode] = useState<boolean>(true);
// Cached ID state
const [hasCachedId, setHasCachedId] = useState<boolean>(false);
// When the validatedShareRoomId from the parent component changes (e.g., after initial fetch), synchronize the local input field's value
useEffect(() => {
setInputFieldValue(currentValidatedShareRoomId);
}, [currentValidatedShareRoomId]);
useEffect(() => {
setHasCachedId(!!getCachedId());
}, []);
const handleInputChange = useCallback(
(e: React.ChangeEvent<HTMLInputElement>) => {
const newValue = e.target.value;
@@ -127,6 +141,31 @@ export function SendTabPanel({
setIsSimpleIdMode(!isSimpleIdMode);
}, [isSimpleIdMode, processRoomIdInput, setInputFieldValue]);
// Save/Use cached ID button handlers
const isSaveEnabled = (inputFieldValue || "").trim().length >= 8;
const handleSaveOrUseCachedId = useCallback(() => {
if (hasCachedId) {
const cached = getCachedId();
if (cached) {
setInputFieldValue(cached);
}
return;
}
// Save current input to cache
const trimmed = (inputFieldValue || "").trim();
if (trimmed.length >= 8) {
setCachedId(trimmed);
setHasCachedId(true);
// Notify via messages on sender side
putMessageInMs(messages.text.ClipboardApp.saveId_success, true);
}
}, [
hasCachedId,
inputFieldValue,
putMessageInMs,
messages.text.ClipboardApp.saveId_success,
]);
return (
<div id="send-panel" role="tabpanel" aria-labelledby="send-tab">
<div className="mb-3 text-sm text-gray-600">
@@ -183,6 +222,27 @@ export function SendTabPanel({
? messages.text.ClipboardApp.html.generateRandomId_tips
: messages.text.ClipboardApp.html.generateSimpleId_tips}
</Button>
{/* Save/Use Cached ID Button in between */}
<Tooltip
content={
hasCachedId
? messages.text.ClipboardApp.html.useCachedId_tips
: messages.text.ClipboardApp.html.saveId_tips
}
>
<span className="inline-block">
<Button
className="w-full sm:w-auto px-4"
variant="outline"
onClick={handleSaveOrUseCachedId}
disabled={!hasCachedId && !isSaveEnabled}
>
{hasCachedId
? messages.text.ClipboardApp.html.useCachedId_dis
: messages.text.ClipboardApp.html.saveId_dis}
</Button>
</span>
</Tooltip>
<Button
className="w-full sm:w-auto px-4"
onClick={() => joinRoom(true, inputFieldValue.trim())}