391 lines
15 KiB
HTML
391 lines
15 KiB
HTML
|
|
<!DOCTYPE html>
|
||
|
|
<html lang="zh-CN">
|
||
|
|
<head>
|
||
|
|
<meta charset="UTF-8">
|
||
|
|
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||
|
|
<title>企业设置管理系统 - 登录</title>
|
||
|
|
<script src="https://cdn.tailwindcss.com"></script>
|
||
|
|
<script src="https://cdnjs.cloudflare.com/ajax/libs/animejs/3.2.1/anime.min.js"></script>
|
||
|
|
<script src="https://cdn.jsdelivr.net/npm/echarts@5.4.3/dist/echarts.min.js"></script>
|
||
|
|
<link href="https://fonts.googleapis.com/css2?family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||
|
|
<style>
|
||
|
|
* {
|
||
|
|
font-family: 'Noto Sans SC', sans-serif;
|
||
|
|
}
|
||
|
|
|
||
|
|
.liquid-bg {
|
||
|
|
position: fixed;
|
||
|
|
top: 0;
|
||
|
|
left: 0;
|
||
|
|
width: 100%;
|
||
|
|
height: 100%;
|
||
|
|
z-index: -1;
|
||
|
|
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||
|
|
}
|
||
|
|
|
||
|
|
.liquid-metal {
|
||
|
|
position: absolute;
|
||
|
|
width: 100%;
|
||
|
|
height: 100%;
|
||
|
|
background:
|
||
|
|
radial-gradient(circle at 20% 80%, rgba(120, 119, 198, 0.3) 0%, transparent 50%),
|
||
|
|
radial-gradient(circle at 80% 20%, rgba(255, 255, 255, 0.15) 0%, transparent 50%),
|
||
|
|
radial-gradient(circle at 40% 40%, rgba(120, 119, 198, 0.4) 0%, transparent 50%);
|
||
|
|
animation: liquidFlow 20s ease-in-out infinite;
|
||
|
|
}
|
||
|
|
|
||
|
|
@keyframes liquidFlow {
|
||
|
|
0%, 100% { transform: translate(0, 0) rotate(0deg); }
|
||
|
|
33% { transform: translate(-20px, -20px) rotate(1deg); }
|
||
|
|
66% { transform: translate(20px, -10px) rotate(-1deg); }
|
||
|
|
}
|
||
|
|
|
||
|
|
.glass-card {
|
||
|
|
background: rgba(255, 255, 255, 0.1);
|
||
|
|
backdrop-filter: blur(20px);
|
||
|
|
border: 1px solid rgba(255, 255, 255, 0.2);
|
||
|
|
box-shadow: 0 25px 45px rgba(0, 0, 0, 0.1);
|
||
|
|
}
|
||
|
|
|
||
|
|
.form-input {
|
||
|
|
background: rgba(255, 255, 255, 0.9);
|
||
|
|
border: 2px solid transparent;
|
||
|
|
transition: all 0.3s ease;
|
||
|
|
}
|
||
|
|
|
||
|
|
.form-input:focus {
|
||
|
|
background: rgba(255, 255, 255, 1);
|
||
|
|
border-color: #4A90E2;
|
||
|
|
box-shadow: 0 0 0 3px rgba(74, 144, 226, 0.1);
|
||
|
|
transform: translateY(-2px);
|
||
|
|
}
|
||
|
|
|
||
|
|
.btn-primary {
|
||
|
|
background: linear-gradient(135deg, #4A90E2 0%, #357ABD 100%);
|
||
|
|
transition: all 0.3s ease;
|
||
|
|
position: relative;
|
||
|
|
overflow: hidden;
|
||
|
|
}
|
||
|
|
|
||
|
|
.btn-primary:hover {
|
||
|
|
transform: translateY(-3px) rotateX(5deg);
|
||
|
|
box-shadow: 0 15px 35px rgba(74, 144, 226, 0.4);
|
||
|
|
}
|
||
|
|
|
||
|
|
.btn-primary:active {
|
||
|
|
transform: translateY(-1px) rotateX(2deg);
|
||
|
|
}
|
||
|
|
|
||
|
|
.floating-particles {
|
||
|
|
position: absolute;
|
||
|
|
width: 100%;
|
||
|
|
height: 100%;
|
||
|
|
overflow: hidden;
|
||
|
|
pointer-events: none;
|
||
|
|
}
|
||
|
|
|
||
|
|
.particle {
|
||
|
|
position: absolute;
|
||
|
|
background: rgba(255, 255, 255, 0.1);
|
||
|
|
border-radius: 50%;
|
||
|
|
animation: float 6s ease-in-out infinite;
|
||
|
|
}
|
||
|
|
|
||
|
|
@keyframes float {
|
||
|
|
0%, 100% { transform: translateY(0px) rotate(0deg); opacity: 0; }
|
||
|
|
50% { transform: translateY(-100px) rotate(180deg); opacity: 1; }
|
||
|
|
}
|
||
|
|
|
||
|
|
.logo-animation {
|
||
|
|
animation: logoFloat 3s ease-in-out infinite;
|
||
|
|
}
|
||
|
|
|
||
|
|
@keyframes logoFloat {
|
||
|
|
0%, 100% { transform: translateY(0px); }
|
||
|
|
50% { transform: translateY(-10px); }
|
||
|
|
}
|
||
|
|
|
||
|
|
.error-shake {
|
||
|
|
animation: shake 0.5s ease-in-out;
|
||
|
|
}
|
||
|
|
|
||
|
|
@keyframes shake {
|
||
|
|
0%, 100% { transform: translateX(0); }
|
||
|
|
25% { transform: translateX(-5px); }
|
||
|
|
75% { transform: translateX(5px); }
|
||
|
|
}
|
||
|
|
</style>
|
||
|
|
</head>
|
||
|
|
<body class="min-h-screen flex items-center justify-center p-4">
|
||
|
|
<div class="liquid-bg">
|
||
|
|
<div class="liquid-metal"></div>
|
||
|
|
<div class="floating-particles" id="particles"></div>
|
||
|
|
</div>
|
||
|
|
|
||
|
|
<div class="glass-card rounded-3xl p-8 w-full max-w-md transform transition-all duration-500 hover:scale-105">
|
||
|
|
<!-- Logo Section -->
|
||
|
|
<div class="text-center mb-8">
|
||
|
|
<div class="logo-animation mb-4">
|
||
|
|
<div class="w-20 h-20 mx-auto bg-gradient-to-br from-blue-400 to-blue-600 rounded-3xl flex items-center justify-center shadow-2xl">
|
||
|
|
<svg class="w-10 h-10 text-white" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||
|
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M19 21V5a2 2 0 00-2-2H7a2 2 0 00-2 2v16m14 0h2m-2 0h-4m-5 0H9m0 0H5m0 0h2M7 7h10M7 11h10M7 15h10"></path>
|
||
|
|
</svg>
|
||
|
|
</div>
|
||
|
|
</div>
|
||
|
|
<h1 class="text-3xl font-bold text-white mb-2">企业设置管理</h1>
|
||
|
|
<p class="text-blue-100 text-sm">安全高效的企业配置平台</p>
|
||
|
|
</div>
|
||
|
|
|
||
|
|
<!-- Login Form -->
|
||
|
|
<form id="loginForm" class="space-y-6">
|
||
|
|
<div class="form-group">
|
||
|
|
<label for="companyId" class="block text-white text-sm font-medium mb-2">企业ID</label>
|
||
|
|
<input
|
||
|
|
type="text"
|
||
|
|
id="companyId"
|
||
|
|
name="companyId"
|
||
|
|
class="form-input w-full px-4 py-3 rounded-xl text-gray-800 placeholder-gray-500 focus:outline-none"
|
||
|
|
placeholder="请输入企业ID"
|
||
|
|
required
|
||
|
|
>
|
||
|
|
<div class="error-message text-red-300 text-xs mt-1 hidden" id="companyIdError"></div>
|
||
|
|
</div>
|
||
|
|
|
||
|
|
<div class="form-group">
|
||
|
|
<label for="password" class="block text-white text-sm font-medium mb-2">登录密码</label>
|
||
|
|
<input
|
||
|
|
type="password"
|
||
|
|
id="password"
|
||
|
|
name="password"
|
||
|
|
class="form-input w-full px-4 py-3 rounded-xl text-gray-800 placeholder-gray-500 focus:outline-none"
|
||
|
|
placeholder="请输入登录密码"
|
||
|
|
required
|
||
|
|
>
|
||
|
|
<div class="error-message text-red-300 text-xs mt-1 hidden" id="passwordError"></div>
|
||
|
|
</div>
|
||
|
|
|
||
|
|
<div class="flex items-center justify-between">
|
||
|
|
<label class="flex items-center">
|
||
|
|
<input type="checkbox" id="rememberMe" class="w-4 h-4 text-blue-600 rounded focus:ring-blue-500">
|
||
|
|
<span class="ml-2 text-sm text-blue-100">记住登录状态</span>
|
||
|
|
</label>
|
||
|
|
<a href="#" class="text-sm text-blue-200 hover:text-white transition-colors">忘记密码?</a>
|
||
|
|
</div>
|
||
|
|
|
||
|
|
<button
|
||
|
|
type="submit"
|
||
|
|
class="btn-primary w-full py-3 px-6 rounded-xl text-white font-medium text-lg focus:outline-none focus:ring-4 focus:ring-blue-300"
|
||
|
|
id="loginBtn"
|
||
|
|
>
|
||
|
|
<span class="btn-text">安全登录</span>
|
||
|
|
<span class="btn-loading hidden">
|
||
|
|
<svg class="animate-spin -ml-1 mr-3 h-5 w-5 text-white inline" xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24">
|
||
|
|
<circle class="opacity-25" cx="12" cy="12" r="10" stroke="currentColor" stroke-width="4"></circle>
|
||
|
|
<path class="opacity-75" fill="currentColor" d="M4 12a8 8 0 018-8V0C5.373 0 0 5.373 0 12h4zm2 5.291A7.962 7.962 0 014 12H0c0 3.042 1.135 5.824 3 7.938l3-2.647z"></path>
|
||
|
|
</svg>
|
||
|
|
验证中...
|
||
|
|
</span>
|
||
|
|
</button>
|
||
|
|
</form>
|
||
|
|
|
||
|
|
<!-- Footer -->
|
||
|
|
<div class="text-center mt-8">
|
||
|
|
<p class="text-blue-200 text-xs">
|
||
|
|
© 2025 企业设置管理系统 | 安全可靠的配置管理平台
|
||
|
|
</p>
|
||
|
|
</div>
|
||
|
|
</div>
|
||
|
|
|
||
|
|
<!-- Success Modal -->
|
||
|
|
<div id="successModal" class="fixed inset-0 bg-black bg-opacity-50 flex items-center justify-center z-50 hidden">
|
||
|
|
<div class="bg-white rounded-2xl p-8 max-w-sm mx-4 transform transition-all duration-300 scale-95">
|
||
|
|
<div class="text-center">
|
||
|
|
<div class="w-16 h-16 mx-auto bg-green-100 rounded-full flex items-center justify-center mb-4">
|
||
|
|
<svg class="w-8 h-8 text-green-500" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||
|
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M5 13l4 4L19 7"></path>
|
||
|
|
</svg>
|
||
|
|
</div>
|
||
|
|
<h3 class="text-lg font-semibold text-gray-900 mb-2">登录成功</h3>
|
||
|
|
<p class="text-gray-600 text-sm mb-6">正在进入企业设置管理平台...</p>
|
||
|
|
<div class="w-full bg-gray-200 rounded-full h-2">
|
||
|
|
<div class="bg-blue-600 h-2 rounded-full transition-all duration-1000" style="width: 0%" id="progressBar"></div>
|
||
|
|
</div>
|
||
|
|
</div>
|
||
|
|
</div>
|
||
|
|
</div>
|
||
|
|
|
||
|
|
<script>
|
||
|
|
// 创建浮动粒子效果
|
||
|
|
function createParticles() {
|
||
|
|
const particlesContainer = document.getElementById('particles');
|
||
|
|
const particleCount = 15;
|
||
|
|
|
||
|
|
for (let i = 0; i < particleCount; i++) {
|
||
|
|
const particle = document.createElement('div');
|
||
|
|
particle.className = 'particle';
|
||
|
|
|
||
|
|
const size = Math.random() * 4 + 2;
|
||
|
|
const left = Math.random() * 100;
|
||
|
|
const animationDelay = Math.random() * 6;
|
||
|
|
const animationDuration = Math.random() * 3 + 4;
|
||
|
|
|
||
|
|
particle.style.width = `${size}px`;
|
||
|
|
particle.style.height = `${size}px`;
|
||
|
|
particle.style.left = `${left}%`;
|
||
|
|
particle.style.bottom = '-10px';
|
||
|
|
particle.style.animationDelay = `${animationDelay}s`;
|
||
|
|
particle.style.animationDuration = `${animationDuration}s`;
|
||
|
|
|
||
|
|
particlesContainer.appendChild(particle);
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
// 表单验证
|
||
|
|
function validateForm() {
|
||
|
|
const companyId = document.getElementById('companyId');
|
||
|
|
const password = document.getElementById('password');
|
||
|
|
let isValid = true;
|
||
|
|
|
||
|
|
// 验证企业ID
|
||
|
|
if (!companyId.value.trim()) {
|
||
|
|
showError('companyIdError', '企业ID不能为空');
|
||
|
|
companyId.classList.add('error-shake');
|
||
|
|
setTimeout(() => companyId.classList.remove('error-shake'), 500);
|
||
|
|
isValid = false;
|
||
|
|
} else {
|
||
|
|
hideError('companyIdError');
|
||
|
|
}
|
||
|
|
|
||
|
|
// 验证密码
|
||
|
|
if (!password.value.trim()) {
|
||
|
|
showError('passwordError', '登录密码不能为空');
|
||
|
|
password.classList.add('error-shake');
|
||
|
|
setTimeout(() => password.classList.remove('error-shake'), 500);
|
||
|
|
isValid = false;
|
||
|
|
} else {
|
||
|
|
hideError('passwordError');
|
||
|
|
}
|
||
|
|
|
||
|
|
return isValid;
|
||
|
|
}
|
||
|
|
|
||
|
|
function showError(elementId, message) {
|
||
|
|
const errorElement = document.getElementById(elementId);
|
||
|
|
errorElement.textContent = message;
|
||
|
|
errorElement.classList.remove('hidden');
|
||
|
|
}
|
||
|
|
|
||
|
|
function hideError(elementId) {
|
||
|
|
const errorElement = document.getElementById(elementId);
|
||
|
|
errorElement.classList.add('hidden');
|
||
|
|
}
|
||
|
|
|
||
|
|
// 登录处理
|
||
|
|
function handleLogin(event) {
|
||
|
|
event.preventDefault();
|
||
|
|
|
||
|
|
if (!validateForm()) {
|
||
|
|
return;
|
||
|
|
}
|
||
|
|
|
||
|
|
const loginBtn = document.getElementById('loginBtn');
|
||
|
|
const btnText = loginBtn.querySelector('.btn-text');
|
||
|
|
const btnLoading = loginBtn.querySelector('.btn-loading');
|
||
|
|
|
||
|
|
// 显示加载状态
|
||
|
|
btnText.classList.add('hidden');
|
||
|
|
btnLoading.classList.remove('hidden');
|
||
|
|
loginBtn.disabled = true;
|
||
|
|
|
||
|
|
// 模拟登录验证
|
||
|
|
setTimeout(() => {
|
||
|
|
// 保存登录状态
|
||
|
|
const rememberMe = document.getElementById('rememberMe').checked;
|
||
|
|
const loginData = {
|
||
|
|
companyId: document.getElementById('companyId').value,
|
||
|
|
loginTime: new Date().toISOString(),
|
||
|
|
rememberMe: rememberMe
|
||
|
|
};
|
||
|
|
|
||
|
|
if (rememberMe) {
|
||
|
|
localStorage.setItem('companyLogin', JSON.stringify(loginData));
|
||
|
|
} else {
|
||
|
|
sessionStorage.setItem('companyLogin', JSON.stringify(loginData));
|
||
|
|
}
|
||
|
|
|
||
|
|
// 显示成功模态框
|
||
|
|
showSuccessModal();
|
||
|
|
|
||
|
|
// 3秒后跳转到设置页面
|
||
|
|
setTimeout(() => {
|
||
|
|
window.location.href = 'settings.html';
|
||
|
|
}, 3000);
|
||
|
|
|
||
|
|
}, 2000);
|
||
|
|
}
|
||
|
|
|
||
|
|
// 显示成功模态框
|
||
|
|
function showSuccessModal() {
|
||
|
|
const modal = document.getElementById('successModal');
|
||
|
|
const progressBar = document.getElementById('progressBar');
|
||
|
|
|
||
|
|
modal.classList.remove('hidden');
|
||
|
|
|
||
|
|
// 动画显示模态框
|
||
|
|
anime({
|
||
|
|
targets: modal.querySelector('.bg-white'),
|
||
|
|
scale: [0.95, 1],
|
||
|
|
opacity: [0, 1],
|
||
|
|
duration: 300,
|
||
|
|
easing: 'easeOutQuad'
|
||
|
|
});
|
||
|
|
|
||
|
|
// 进度条动画
|
||
|
|
anime({
|
||
|
|
targets: progressBar,
|
||
|
|
width: '100%',
|
||
|
|
duration: 3000,
|
||
|
|
easing: 'linear'
|
||
|
|
});
|
||
|
|
}
|
||
|
|
|
||
|
|
// 初始化
|
||
|
|
document.addEventListener('DOMContentLoaded', function() {
|
||
|
|
createParticles();
|
||
|
|
|
||
|
|
// 检查是否已登录
|
||
|
|
const savedLogin = localStorage.getItem('companyLogin') || sessionStorage.getItem('companyLogin');
|
||
|
|
if (savedLogin) {
|
||
|
|
const loginData = JSON.parse(savedLogin);
|
||
|
|
document.getElementById('companyId').value = loginData.companyId || '';
|
||
|
|
document.getElementById('rememberMe').checked = loginData.rememberMe || false;
|
||
|
|
}
|
||
|
|
|
||
|
|
// 表单提交事件
|
||
|
|
document.getElementById('loginForm').addEventListener('submit', handleLogin);
|
||
|
|
|
||
|
|
// 输入框聚焦动画
|
||
|
|
const inputs = document.querySelectorAll('.form-input');
|
||
|
|
inputs.forEach(input => {
|
||
|
|
input.addEventListener('focus', function() {
|
||
|
|
anime({
|
||
|
|
targets: this,
|
||
|
|
scale: [1, 1.02],
|
||
|
|
duration: 200,
|
||
|
|
easing: 'easeOutQuad'
|
||
|
|
});
|
||
|
|
});
|
||
|
|
|
||
|
|
input.addEventListener('blur', function() {
|
||
|
|
anime({
|
||
|
|
targets: this,
|
||
|
|
scale: [1.02, 1],
|
||
|
|
duration: 200,
|
||
|
|
easing: 'easeOutQuad'
|
||
|
|
});
|
||
|
|
});
|
||
|
|
});
|
||
|
|
});
|
||
|
|
</script>
|
||
|
|
</body>
|
||
|
|
</html>
|