我正在使用 react-redux 来存储我的消息。
消息,列表类型;的每个元素都包含一个唯一的 id、一条消息和严重性,即 messages = [{'id': uuidv4(), 'message': 'invalid input', 'severity': 'error'}, {'id': uuidv4(), 'message': 'document updated successfully', 'severity': 'success'}] 其中 uuidv4() import { v4 as uuidv4 } from "uuid";。我为每个消息 ID 使用 uuid 而不是列表中的索引,因为一旦删除一个消息,不同的消息可以共享相同的索引。这种方法解决了 <Stack /> 仅显示 1 个 <Snackbar />(或多个 Snackbars 但彼此重叠)的问题。
/// reducer
case SNACKBAR_WRITE:
return {
...state,
messages: [
...state.messages,
{
id: uuidv4(),
message: payload.message,
severity: payload.severity,
},
],
};
case SNACKBAR_DELETE:
return {
...state,
messages: state.messages.filter((message) => message.id !== payload),
};
/// custom component
import React, { useEffect } from "react";
import { connect } from "react-redux";
import { remove_snackbar } from "../../actions/auth";
import { Alert } from "@mui/material";
const CustomAlert = ({ message, remove_snackbar }) => {
useEffect(() => {
setTimeout(function () {
remove_snackbar(message.id);
}, 8000);
}, [message, remove_snackbar]);
const handleAlertClose = (event, reason) => {
if (reason === "clickaway") {
return;
}
remove_snackbar(message.id);
};
return (
<Alert
onClose={handleAlertClose}
elevation={6}
variant="filled"
severity={message.severity}
>
{message.message}
</Alert>
);
};
export default connect(null, { remove_snackbar })(CustomAlert);
///main jsx
<Stack sx={{ position: "absolute", bottom: 24, right: 24 }} spacing={2}>
{messages.map((message) => (<CustomAlert message={message} key={message.id} />))}
</Stack>