130 lines
4.0 KiB
TypeScript
130 lines
4.0 KiB
TypeScript
|
|
import React, { useState } from 'react';
|
|||
|
|
import { Form, Input, Button, message } from 'antd';
|
|||
|
|
import { UserOutlined, LockOutlined, SafetyCertificateOutlined } from '@ant-design/icons';
|
|||
|
|
import { history } from '@umijs/max';
|
|||
|
|
import './index.less';
|
|||
|
|
|
|||
|
|
interface LoginForm {
|
|||
|
|
username: string;
|
|||
|
|
password: string;
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
const LoginPage: React.FC = () => {
|
|||
|
|
const [loading, setLoading] = useState(false);
|
|||
|
|
|
|||
|
|
const onFinish = async (values: LoginForm) => {
|
|||
|
|
setLoading(true);
|
|||
|
|
try {
|
|||
|
|
// 模拟登录验证
|
|||
|
|
if (values.username === 'admin' && values.password === '123456') {
|
|||
|
|
message.success('登录成功!');
|
|||
|
|
// 存储登录状态
|
|||
|
|
localStorage.setItem('isLoggedIn', 'true');
|
|||
|
|
localStorage.setItem('username', values.username);
|
|||
|
|
// 跳转到镜像列表页面
|
|||
|
|
history.push('/images');
|
|||
|
|
} else {
|
|||
|
|
message.error('用户名或密码错误!');
|
|||
|
|
}
|
|||
|
|
} catch (error) {
|
|||
|
|
message.error('登录失败,请重试!');
|
|||
|
|
} finally {
|
|||
|
|
setLoading(false);
|
|||
|
|
}
|
|||
|
|
};
|
|||
|
|
|
|||
|
|
return (
|
|||
|
|
<div className="login-container">
|
|||
|
|
{/* 左侧品牌区域 */}
|
|||
|
|
<div className="login-left">
|
|||
|
|
<div className="brand-content">
|
|||
|
|
<div className="brand-logo">
|
|||
|
|
<SafetyCertificateOutlined className="logo-icon" />
|
|||
|
|
<h1 className="brand-title">紫光汇智</h1>
|
|||
|
|
</div>
|
|||
|
|
<div className="brand-subtitle">VDI 虚拟桌面管理平台</div>
|
|||
|
|
<div className="brand-description">
|
|||
|
|
<p>专业的虚拟桌面基础设施解决方案</p>
|
|||
|
|
<p>提供安全、高效、灵活的桌面云服务</p>
|
|||
|
|
</div>
|
|||
|
|
<div className="brand-features">
|
|||
|
|
<div className="feature-item">
|
|||
|
|
<span className="feature-icon">🔒</span>
|
|||
|
|
<span>安全可靠</span>
|
|||
|
|
</div>
|
|||
|
|
<div className="feature-item">
|
|||
|
|
<span className="feature-icon">⚡</span>
|
|||
|
|
<span>高效管理</span>
|
|||
|
|
</div>
|
|||
|
|
<div className="feature-item">
|
|||
|
|
<span className="feature-icon">🔄</span>
|
|||
|
|
<span>灵活部署</span>
|
|||
|
|
</div>
|
|||
|
|
</div>
|
|||
|
|
</div>
|
|||
|
|
</div>
|
|||
|
|
|
|||
|
|
{/* 右侧登录区域 */}
|
|||
|
|
<div className="login-right">
|
|||
|
|
<div className="login-form-container">
|
|||
|
|
<div className="login-header">
|
|||
|
|
<h2 className="login-title">系统登录</h2>
|
|||
|
|
<p className="login-subtitle">欢迎使用VDI管理平台</p>
|
|||
|
|
</div>
|
|||
|
|
|
|||
|
|
<Form
|
|||
|
|
name="login"
|
|||
|
|
onFinish={onFinish}
|
|||
|
|
autoComplete="off"
|
|||
|
|
size="large"
|
|||
|
|
className="login-form"
|
|||
|
|
>
|
|||
|
|
<Form.Item
|
|||
|
|
name="username"
|
|||
|
|
rules={[{ required: true, message: '请输入用户名!' }]}
|
|||
|
|
>
|
|||
|
|
<Input
|
|||
|
|
prefix={<UserOutlined className="input-icon" />}
|
|||
|
|
placeholder="请输入用户名"
|
|||
|
|
className="login-input"
|
|||
|
|
/>
|
|||
|
|
</Form.Item>
|
|||
|
|
|
|||
|
|
<Form.Item
|
|||
|
|
name="password"
|
|||
|
|
rules={[{ required: true, message: '请输入密码!' }]}
|
|||
|
|
>
|
|||
|
|
<Input.Password
|
|||
|
|
prefix={<LockOutlined className="input-icon" />}
|
|||
|
|
placeholder="请输入密码"
|
|||
|
|
className="login-input"
|
|||
|
|
/>
|
|||
|
|
</Form.Item>
|
|||
|
|
|
|||
|
|
<Form.Item>
|
|||
|
|
<Button
|
|||
|
|
type="primary"
|
|||
|
|
htmlType="submit"
|
|||
|
|
loading={loading}
|
|||
|
|
className="login-button"
|
|||
|
|
block
|
|||
|
|
>
|
|||
|
|
{loading ? '登录中...' : '登录'}
|
|||
|
|
</Button>
|
|||
|
|
</Form.Item>
|
|||
|
|
</Form>
|
|||
|
|
|
|||
|
|
<div className="login-tips">
|
|||
|
|
<p>演示账号:admin / 123456</p>
|
|||
|
|
</div>
|
|||
|
|
|
|||
|
|
<div className="login-footer">
|
|||
|
|
<p>© 2025 紫光汇智科技有限公司 版权所有</p>
|
|||
|
|
</div>
|
|||
|
|
</div>
|
|||
|
|
</div>
|
|||
|
|
</div>
|
|||
|
|
);
|
|||
|
|
};
|
|||
|
|
|
|||
|
|
export default LoginPage;
|