refactor(mui): ConfirmDialog freezes content via derive-state-from-props (no ref-in-render)
Replaces the useRef-during-render snapshot with React's blessed 'adjust state when a prop changes' pattern (useState + guarded setState during render). Render-pure, same self-contained behavior. Avoids writing to a ref during render. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -1,4 +1,4 @@
|
|||||||
import { useRef } from "react";
|
import { useState } from "react";
|
||||||
import Dialog from "@mui/material/Dialog";
|
import Dialog from "@mui/material/Dialog";
|
||||||
import DialogTitle from "@mui/material/DialogTitle";
|
import DialogTitle from "@mui/material/DialogTitle";
|
||||||
import DialogContent from "@mui/material/DialogContent";
|
import DialogContent from "@mui/material/DialogContent";
|
||||||
@@ -30,11 +30,16 @@ export default function ConfirmDialog({
|
|||||||
confirmVariant = "primary",
|
confirmVariant = "primary",
|
||||||
loading = false,
|
loading = false,
|
||||||
}: ConfirmDialogProps) {
|
}: ConfirmDialogProps) {
|
||||||
// Retain the last shown title/message so the close (fade-out) transition
|
// Freeze the shown title/message while closing, so the fade-out transition
|
||||||
// doesn't flash empty when the caller clears its source data (e.g. sets the
|
// never flashes empty when the caller clears its source data (e.g. sets the
|
||||||
// selected row to null) at the same moment it closes the dialog.
|
// selected row to null) at the same instant it closes the dialog. This is
|
||||||
const shown = useRef({ title, message });
|
// React's "adjust state from props during render" pattern: update only while
|
||||||
if (isOpen) shown.current = { title, message };
|
// open, keep the last values once closed. (Self-contained — callers can clear
|
||||||
|
// their data on close however they like.)
|
||||||
|
const [shown, setShown] = useState({ title, message });
|
||||||
|
if (isOpen && (shown.title !== title || shown.message !== message)) {
|
||||||
|
setShown({ title, message });
|
||||||
|
}
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Dialog
|
<Dialog
|
||||||
@@ -42,9 +47,9 @@ export default function ConfirmDialog({
|
|||||||
onClose={loading ? undefined : onClose}
|
onClose={loading ? undefined : onClose}
|
||||||
slotProps={{ paper: { sx: { borderRadius: 3 } } }}
|
slotProps={{ paper: { sx: { borderRadius: 3 } } }}
|
||||||
>
|
>
|
||||||
<DialogTitle>{shown.current.title}</DialogTitle>
|
<DialogTitle>{shown.title}</DialogTitle>
|
||||||
<DialogContent>
|
<DialogContent>
|
||||||
<DialogContentText>{shown.current.message}</DialogContentText>
|
<DialogContentText>{shown.message}</DialogContentText>
|
||||||
</DialogContent>
|
</DialogContent>
|
||||||
<DialogActions sx={{ px: 3, pb: 2 }}>
|
<DialogActions sx={{ px: 3, pb: 2 }}>
|
||||||
<MuiButton onClick={onClose} color="inherit" disabled={loading}>
|
<MuiButton onClick={onClose} color="inherit" disabled={loading}>
|
||||||
|
|||||||
Reference in New Issue
Block a user