fix: 公告弹窗改为 CSS Module 规范
All checks were successful
Build and Deploy / build-and-deploy (push) Successful in 10m8s

inline style 改为 CSS Module,z-index/圆角/关闭按钮与其他弹窗统一

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
seaislee1209 2026-03-23 22:13:42 +08:00
parent 0ab5523ed1
commit f4255a04ee
2 changed files with 100 additions and 41 deletions

View File

@ -0,0 +1,86 @@
.overlay {
position: fixed;
inset: 0;
background: rgba(0, 0, 0, 0.6);
display: flex;
align-items: center;
justify-content: center;
z-index: 300;
}
.modal {
background: #16161e;
border: 1px solid var(--color-border-card);
border-radius: var(--radius-card);
max-width: 520px;
width: 90vw;
max-height: 75vh;
display: flex;
flex-direction: column;
}
.header {
display: flex;
justify-content: space-between;
align-items: center;
padding: 20px 32px 12px;
flex-shrink: 0;
border-bottom: 1px solid rgba(255, 255, 255, 0.06);
}
.title {
font-size: 16px;
font-weight: 600;
color: var(--color-text-primary);
}
.closeBtn {
background: none;
border: none;
color: var(--color-text-secondary);
cursor: pointer;
padding: 4px;
display: flex;
align-items: center;
transition: color 0.15s;
}
.closeBtn:hover {
color: var(--color-text-primary);
}
.content {
font-size: 14px;
line-height: 1.8;
color: var(--color-text-primary);
word-break: break-word;
padding: 16px 40px;
overflow-y: auto;
scrollbar-width: none;
flex: 1;
}
.content::-webkit-scrollbar {
display: none;
}
.footer {
text-align: center;
padding: 16px 0 20px;
flex-shrink: 0;
}
.confirmBtn {
padding: 8px 32px;
background: var(--color-primary);
border: none;
border-radius: 8px;
color: #fff;
font-size: 14px;
cursor: pointer;
transition: opacity 0.15s;
}
.confirmBtn:hover {
opacity: 0.85;
}

View File

@ -1,5 +1,6 @@
import { useEffect, useState, useCallback } from 'react';
import { videoApi } from '../lib/api';
import styles from './AnnouncementModal.module.css';
interface Props {
/** If true, force show even if already read (for manual open) */
@ -31,51 +32,23 @@ export function AnnouncementModal({ forceOpen, onClose }: Props) {
if (!visible || !content) return null;
return (
<div
style={{
position: 'fixed', inset: 0, zIndex: 400,
background: 'rgba(0, 0, 0, 0.6)',
display: 'flex', alignItems: 'center', justifyContent: 'center',
}}
onMouseDown={(e) => { if (e.target === e.currentTarget) handleClose(); }}
>
<div style={{
background: '#16161e', border: '1px solid var(--color-border-card)',
borderRadius: 12, padding: '28px 32px', maxWidth: 520, width: '90vw',
maxHeight: '70vh', overflowY: 'auto',
scrollbarWidth: 'none',
}}>
<div style={{
display: 'flex', justifyContent: 'space-between', alignItems: 'center',
marginBottom: 16,
}}>
<span style={{ fontSize: 16, fontWeight: 600, color: 'var(--color-text-primary)' }}>
📢
</span>
<button
onClick={handleClose}
style={{
background: 'none', border: 'none', color: 'var(--color-text-secondary)',
cursor: 'pointer', fontSize: 18, padding: 4,
}}
></button>
<div className={styles.overlay} onMouseDown={(e) => { if (e.target === e.currentTarget) handleClose(); }}>
<div className={styles.modal}>
<div className={styles.header}>
<span className={styles.title}></span>
<button className={styles.closeBtn} onClick={handleClose}>
<svg width="18" height="18" viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2" strokeLinecap="round">
<line x1="18" y1="6" x2="6" y2="18" />
<line x1="6" y1="6" x2="18" y2="18" />
</svg>
</button>
</div>
<div
style={{
fontSize: 14, lineHeight: 1.8, color: 'var(--color-text-primary)',
wordBreak: 'break-word', padding: '0 8px',
}}
className={styles.content}
dangerouslySetInnerHTML={{ __html: `<style>li{margin-left:16px}</style>${content}` }}
/>
<div style={{ textAlign: 'center', marginTop: 20 }}>
<button
onClick={handleClose}
style={{
padding: '8px 32px', background: 'var(--color-primary)',
border: 'none', borderRadius: 8, color: '#fff', fontSize: 14,
cursor: 'pointer',
}}
>
<div className={styles.footer}>
<button className={styles.confirmBtn} onClick={handleClose}>
</button>
</div>