diff --git a/frontend/src/app/globals.css b/frontend/src/app/globals.css
index 2b1b002..bcc1964 100644
--- a/frontend/src/app/globals.css
+++ b/frontend/src/app/globals.css
@@ -38,6 +38,7 @@ body {
font-family: Arial, Helvetica, sans-serif;
padding-top: env(safe-area-inset-top);
padding-bottom: env(safe-area-inset-bottom);
+ background: linear-gradient(to bottom, #0f172a 0%, #0f172a 5%, #581c87 50%, #0f172a 95%, #0f172a 100%);
}
/* 自定义滚动条样式 - 深色主题 */
diff --git a/frontend/src/app/layout.tsx b/frontend/src/app/layout.tsx
index afd5c76..20a3dc2 100644
--- a/frontend/src/app/layout.tsx
+++ b/frontend/src/app/layout.tsx
@@ -33,14 +33,9 @@ export default function RootLayout({
children: React.ReactNode;
}>) {
return (
-
+
diff --git a/frontend/src/app/page.tsx b/frontend/src/app/page.tsx
index a200c91..d6d415a 100644
--- a/frontend/src/app/page.tsx
+++ b/frontend/src/app/page.tsx
@@ -6,6 +6,8 @@ import Link from "next/link";
import api from "@/lib/axios";
import { useAuth } from "@/contexts/AuthContext";
import { useTask } from "@/contexts/TaskContext";
+import AccountSettingsDropdown from "@/components/AccountSettingsDropdown";
+import VideoPreviewModal from "@/components/VideoPreviewModal";
const API_BASE = typeof window === 'undefined'
? 'http://localhost:8006'
@@ -56,215 +58,12 @@ const formatDate = (timestamp: number) => {
return `${year}/${month}/${day} ${hour}:${minute}`;
};
-// 账户设置下拉菜单组件
-function AccountSettingsDropdown() {
- const { user } = useAuth();
- const [isOpen, setIsOpen] = useState(false);
- const [showPasswordModal, setShowPasswordModal] = useState(false);
- const [oldPassword, setOldPassword] = useState('');
- const [newPassword, setNewPassword] = useState('');
- const [confirmPassword, setConfirmPassword] = useState('');
- const [error, setError] = useState('');
- const [success, setSuccess] = useState('');
- const [loading, setLoading] = useState(false);
- const dropdownRef = useRef(null);
- // 点击外部关闭菜单
- useEffect(() => {
- const handleClickOutside = (event: MouseEvent) => {
- if (dropdownRef.current && !dropdownRef.current.contains(event.target as Node)) {
- setIsOpen(false);
- }
- };
- if (isOpen) {
- document.addEventListener('mousedown', handleClickOutside);
- }
- return () => {
- document.removeEventListener('mousedown', handleClickOutside);
- };
- }, [isOpen]);
-
- // 格式化有效期
- const formatExpiry = (expiresAt: string | null) => {
- if (!expiresAt) return '永久有效';
- const date = new Date(expiresAt);
- return `${date.getFullYear()}-${String(date.getMonth() + 1).padStart(2, '0')}-${String(date.getDate()).padStart(2, '0')}`;
- };
-
- const handleLogout = async () => {
- if (confirm('确定要退出登录吗?')) {
- try {
- await api.post('/api/auth/logout');
- } catch (e) { }
- window.location.href = '/login';
- }
- };
-
- const handleChangePassword = async (e: React.FormEvent) => {
- e.preventDefault();
- setError('');
- setSuccess('');
-
- if (newPassword !== confirmPassword) {
- setError('两次输入的新密码不一致');
- return;
- }
-
- if (newPassword.length < 6) {
- setError('新密码长度至少6位');
- return;
- }
-
- setLoading(true);
- try {
- const res = await api.post('/api/auth/change-password', {
- old_password: oldPassword,
- new_password: newPassword
- });
- if (res.data.success) {
- setSuccess('密码修改成功,正在跳转登录页...');
- // 清除登录状态并跳转
- setTimeout(async () => {
- try {
- await api.post('/api/auth/logout');
- } catch (e) { }
- window.location.href = '/login';
- }, 1500);
- } else {
- setError(res.data.message || '修改失败');
- }
- } catch (err: any) {
- setError(err.response?.data?.detail || '修改失败,请重试');
- } finally {
- setLoading(false);
- }
- };
-
- return (
-
-
-
- {/* 下拉菜单 */}
- {isOpen && (
-
- {/* 有效期显示 */}
-
-
账户有效期
-
- {user?.expires_at ? formatExpiry(user.expires_at) : '永久有效'}
-
-
-
-
-
- )}
-
- {/* 修改密码弹窗 */}
- {showPasswordModal && (
-
- )}
-
- );
-}
export default function Home() {
const [materials, setMaterials] = useState([]);
const [selectedMaterial, setSelectedMaterial] = useState("");
+ const [previewMaterial, setPreviewMaterial] = useState(null);
const [text, setText] = useState("");
const [voice, setVoice] = useState("zh-CN-YunxiNeural");
@@ -856,6 +655,18 @@ export default function Home() {
{m.size_mb.toFixed(1)} MB
+