This commit is contained in:
2026-08-13 11:31:27 +08:00
parent 437be9dac0
commit fe855e0fa2
3 changed files with 142 additions and 126 deletions
File diff suppressed because one or more lines are too long
+1 -1
View File
@@ -27,7 +27,7 @@
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin />
<link href="https://fonts.googleapis.com/css2?family=Outfit:wght@300;400;500;600;700&display=swap" rel="stylesheet" />
<title>民众智创</title>
<script type="module" crossorigin src="/assets/index-BcfRvOz8.js"></script>
<script type="module" crossorigin src="/assets/index-BWkfqdZQ.js"></script>
<link rel="stylesheet" crossorigin href="/assets/index-DSYnuUvx.css">
</head>
<body>
@@ -1,5 +1,5 @@
import React, { useEffect, useState, useCallback, useRef } from 'react';
import { Layout, Avatar, Dropdown, Space, Modal, Form, Input, message, Tag, Button, Typography, Radio, Drawer, Tabs, Progress, Collapse, ConfigProvider } from 'antd';
import { Layout, Avatar, Dropdown, Space, Modal, Form, Input, message, notification, Tag, Button, Typography, Radio, Drawer, Tabs, Progress, Collapse, ConfigProvider } from 'antd';
import { QRCodeSVG } from 'qrcode.react';
import {
PlayCircleOutlined,
@@ -64,7 +64,6 @@ import { getMenuConfigs, getCreditProductCatalog, getPaymentMethods, createRecha
import type { CreditProduct, CreditProductCatalog } from '../../types';
import NotificationPopup from '../NotificationPopup';
import ActivityBanner from './ActivityBanner';
import KickedOutModal from '../KickedOutModal';
import './AppLayout.css';
@@ -501,7 +500,6 @@ const AppLayout: React.FC = () => {
});
const [siteInfoLoading, setSiteInfoLoading] = useState(!localStorage.getItem('siteInfo'));
const [bannerVisible, setBannerVisible] = useState(false);
const [kickedOutVisible, setKickedOutVisible] = useState(false);
// 资源存储容量(从 getUser().resource_capacity 获取)
const [resourceCapacity, setResourceCapacity] = useState<{
@@ -517,12 +515,31 @@ const AppLayout: React.FC = () => {
const [isMobile, setIsMobile] = useState(false);
const [operationManualUrl, setOperationManualUrl] = useState('');
// 监听"被踢出"事件 — 单设备登录互斥
// 监听"被踢出"事件 — 单设备登录互斥,显示顶部通知
useEffect(() => {
const handler = () => setKickedOutVisible(true);
window.addEventListener('kicked-out', handler);
return () => window.removeEventListener('kicked-out', handler);
}, []);
const handleKickedOut = () => {
notification.warning({
message: '登录提示',
description: '您的账号已在其他设备登录,请重新登录',
placement: 'top',
duration: 0, // 不自动关闭
btn: (
<Button
type="primary"
size="small"
onClick={() => {
localStorage.removeItem('token');
navigate('/login');
}}
>
</Button>
),
});
};
window.addEventListener('kicked-out', handleKickedOut);
return () => window.removeEventListener('kicked-out', handleKickedOut);
}, [navigate]);
useEffect(() => {
getSiteInfo().then(info => {
@@ -1038,7 +1055,6 @@ const AppLayout: React.FC = () => {
overflow: 'hidden',
}}>
<ActivityBanner onVisibilityChange={(v) => setBannerVisible(v)} />
<KickedOutModal visible={kickedOutVisible} />
<div style={{ display: 'flex', position: 'relative', padding: 4, gap: 12, flex: 1, minHeight: 0, overflow: 'hidden' }}>
<div className="desktop-sidebar" style={{
width: sidebarW, position: 'sticky', top: 4, alignSelf: 'flex-start', zIndex: 100,