mirror of
https://github.com/Stirling-Tools/Stirling-PDF.git
synced 2026-09-02 21:03:34 +03:00
Signing UI edge-case cleanup (#6849)
This commit is contained in:
@@ -130,7 +130,12 @@ const ShareManagementModal: React.FC<ShareManagementModalProps> = ({
|
||||
}, [config?.frontendUrl]);
|
||||
|
||||
const loadShareLinks = useCallback(async () => {
|
||||
if (!file.remoteStorageId) return;
|
||||
if (!file.remoteStorageId) {
|
||||
// No remote file yet — clear any leftover state from a previously opened file.
|
||||
setShareLinks([]);
|
||||
setSharedUsers([]);
|
||||
return;
|
||||
}
|
||||
setIsLoading(true);
|
||||
setErrorMessage(null);
|
||||
try {
|
||||
@@ -161,6 +166,10 @@ const ShareManagementModal: React.FC<ShareManagementModalProps> = ({
|
||||
|
||||
useEffect(() => {
|
||||
if (opened) {
|
||||
// Clear the previous file's data before loading so a stale list is never
|
||||
// shown (and never targeted by a Remove click) while the new file resolves.
|
||||
setShareLinks([]);
|
||||
setSharedUsers([]);
|
||||
loadShareLinks();
|
||||
setActivityMap({});
|
||||
setShareRole("editor");
|
||||
|
||||
@@ -331,6 +331,12 @@ export const SignaturePreviewLayer = memo(function SignaturePreviewLayer({
|
||||
newY = startTop + (startHeight - newHeight);
|
||||
}
|
||||
|
||||
// Keep the box on-page (mirrors the placement clamp).
|
||||
newWidth = Math.min(newWidth, 1);
|
||||
newHeight = Math.min(newHeight, 1);
|
||||
newX = Math.max(0, Math.min(newX, 1 - newWidth));
|
||||
newY = Math.max(0, Math.min(newY, 1 - newHeight));
|
||||
|
||||
onChange(
|
||||
previews.map((p) =>
|
||||
p.id === preview.id
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import { useCallback, useEffect, useState } from "react";
|
||||
import { useCallback, useEffect, useRef, useState } from "react";
|
||||
import { useTranslation } from "react-i18next";
|
||||
import apiClient from "@app/services/apiClient";
|
||||
import { alert } from "@app/components/toast";
|
||||
@@ -103,6 +103,10 @@ export function useSigningSessionController(enabled: boolean) {
|
||||
const [requestData, setRequestData] = useState<SigningRequestData | null>(
|
||||
null,
|
||||
);
|
||||
// The session currently shown in the detail view. A refresh checks this at
|
||||
// resolve time so a request dispatched before navigation is discarded rather
|
||||
// than painting its data onto whatever is now on screen.
|
||||
const openDetailSessionIdRef = useRef<string | null>(null);
|
||||
|
||||
// Leaving the tool (panel unmounts) must not leave the signing document and
|
||||
// overlays lingering on the shared viewer.
|
||||
@@ -111,6 +115,7 @@ export function useSigningSessionController(enabled: boolean) {
|
||||
}, [setOverlay]);
|
||||
|
||||
const backToList = useCallback(() => {
|
||||
openDetailSessionIdRef.current = null;
|
||||
setOverlay(null);
|
||||
setDetailData(null);
|
||||
setRequestData(null);
|
||||
@@ -203,6 +208,9 @@ export function useSigningSessionController(enabled: boolean) {
|
||||
);
|
||||
const session = response.data;
|
||||
markSessionSeen(session.sessionId, countSignedParticipants(session));
|
||||
// Discard a refresh that resolves after the user navigated away, so we
|
||||
// never paint this session's data onto another document.
|
||||
if (openDetailSessionIdRef.current !== session.sessionId) return;
|
||||
setDetailData((prev) => (prev ? { ...prev, session } : prev));
|
||||
// Keep the read-only overlay in sync as participants sign.
|
||||
setOverlay((prev) =>
|
||||
@@ -275,6 +283,8 @@ export function useSigningSessionController(enabled: boolean) {
|
||||
detailResponse.data.myStatus === "NOTIFIED" ||
|
||||
detailResponse.data.myStatus === "VIEWED";
|
||||
|
||||
// Leaving the detail view: stop any in-flight detail refresh from applying.
|
||||
openDetailSessionIdRef.current = null;
|
||||
// Seed the viewer with the document immediately; the request panel enriches
|
||||
// the overlay with interactive placement props once it mounts.
|
||||
setOverlay({ file: pdfFile });
|
||||
@@ -353,6 +363,7 @@ export function useSigningSessionController(enabled: boolean) {
|
||||
}
|
||||
}
|
||||
|
||||
openDetailSessionIdRef.current = session.sessionId;
|
||||
setOverlay({
|
||||
file: pdfFile,
|
||||
signaturePreviews: computeWetSignaturePreviews(detailResponse.data),
|
||||
|
||||
Reference in New Issue
Block a user