udpate login.html

This commit is contained in:
backuppc
2025-07-10 14:36:05 +09:00
parent 43526a26ec
commit 26cb328f8f
31 changed files with 866 additions and 543 deletions

View File

@@ -233,7 +233,7 @@
data.forEach(item => {
tableRows += `
<tr class="hover:bg-white/5 transition-colors">
<td class="px-6 py-4 whitespace-nowrap text-white">${item.uid || '-'}</td>
<td class="px-6 py-4 whitespace-nowrap text-white">${item.name || '-'}(${item.uid})</td>
<td class="px-6 py-4 whitespace-nowrap">
<span class="inline-flex items-center px-2.5 py-0.5 rounded-full text-xs font-medium bg-warning-500/20 text-warning-300">
${item.cate || '-'}

View File

@@ -1,114 +0,0 @@
<!DOCTYPE html>
<html lang="ko">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>근태현황 대시보드</title>
<link href="https://cdn.jsdelivr.net/npm/bootstrap@5.3.0/dist/css/bootstrap.min.css" rel="stylesheet">
</head>
<body>
<div class="container py-5">
<div class="row mb-4">
<div class="col-md-3">
<div class="card text-center">
<div class="card-body">
<h5 class="card-title">출근</h5>
<p class="card-text fs-2" id="presentCount">0</p>
</div>
</div>
</div>
<div class="col-md-3">
<div class="card text-center">
<div class="card-body">
<h5 class="card-title">휴가</h5>
<p class="card-text fs-2" id="leaveCount">0</p>
</div>
</div>
</div>
<div class="col-md-3">
<div class="card text-center">
<div class="card-body">
<h5 class="card-title">휴가요청</h5>
<p class="card-text fs-2" id="leaveCount">0</p>
</div>
</div>
</div>
<div class="col-md-3">
<div class="card text-center">
<div class="card-body">
<h5 class="card-title">구매요청</h5>
<p class="card-text fs-2" id="leaveCount">0</p>
</div>
</div>
</div>
</div>
<div class="card">
<div class="card-header">
휴가자 현황
</div>
<div class="card-body p-0">
<table class="table mb-0">
<thead class="table-light">
<tr>
<th>이름</th>
<th>출근 시간</th>
<th>퇴근 시간</th>
<th>상태</th>
</tr>
</thead>
<tbody id="attendanceTable">
<!-- 데이터가 여기에 표시됩니다 -->
</tbody>
</table>
</div>
</div>
</div>
<script>
// 샘플 데이터
const attendanceData = [
{ name: '홍길동', checkIn: '09:01', checkOut: '18:00', status: '지각' },
{ name: '김철수', checkIn: '08:55', checkOut: '18:05', status: '정상' },
{ name: '이영희', checkIn: '-', checkOut: '-', status: '결근' },
{ name: '박민수', checkIn: '09:00', checkOut: '18:10', status: '정상' },
{ name: '최지우', checkIn: '09:20', checkOut: '18:00', status: '지각' }
];
function updateDashboard(data) {
let present = 0, leave = 0, late = 0, absent = 0;
let tableRows = '';
data.forEach(item => {
if (item.status === '정상' || item.status === '지각') present++;
if (item.checkOut !== '-') leave++;
if (item.status === '지각') late++;
if (item.status === '결근') absent++;
tableRows += `<tr>
<td>${item.name}</td>
<td>${item.checkIn}</td>
<td>${item.checkOut}</td>
<td>${item.status}</td>
</tr>`;
});
}
// 페이지 로드 시 대시보드 업데이트
updateDashboard(attendanceData);
// 휴가 인원 Ajax 업데이트
function updateLeaveCount() {
fetch('http://127.0.0.1:9000/Dashboard/TodayCountH')
.then(response => response.text())
.then(data => {
// 수신된 데이터가 "1" 형태로 반환되므로, 쌍따옴표를 제거하고 숫자로 변환
const cleanData = data.replace(/"/g, '');
document.getElementById('leaveCount').textContent = parseInt(cleanData, 10);
})
.catch(error => console.error('휴가 인원 업데이트 중 오류 발생:', error));
}
// 페이지 로드 시 휴가 인원 업데이트
updateLeaveCount();
</script>
<script src="https://cdn.jsdelivr.net/npm/bootstrap@5.3.0/dist/js/bootstrap.bundle.min.js"></script>
</body>
</html>

View File

@@ -116,6 +116,17 @@
transform: translateY(-1.5rem) scale(0.85);
color: #3b82f6;
}
/* 드롭다운 스타일 */
select.input-field option {
background-color: #1f2937;
color: white;
}
select.input-field:focus option:checked {
background-color: #3b82f6;
}
select.input-field option:hover {
background-color: #374151;
}
</style>
</head>
<body class="gradient-bg min-h-screen flex items-center justify-center p-4">
@@ -133,8 +144,28 @@
<p class="text-white/70 text-sm">로그인하여 시스템에 접속하세요</p>
</div>
<!-- 로그인 폼 -->
<!-- 로그인 폼 -->
<form id="loginForm" class="space-y-6 animate-slide-up">
<!-- Gcode 드롭다운 -->
<div class="relative">
<select
id="gcode"
name="gcode"
class="input-field w-full px-4 py-3 bg-white/10 border border-white/20 rounded-xl text-white focus:outline-none focus:border-primary-400 input-focus appearance-none"
required
>
<option value="" class="text-gray-800">부서를 선택하세요</option>
</select>
<label for="gcode" class="floating-label absolute left-4 top-3 text-white/60 text-sm pointer-events-none">
부서 선택
</label>
<div class="absolute right-3 top-3 pointer-events-none">
<svg class="w-5 h-5 text-white/40" fill="none" stroke="currentColor" viewBox="0 0 24 24">
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M19 9l-7 7-7-7"></path>
</svg>
</div>
</div>
<!-- 사용자 ID 입력 -->
<div class="relative">
<input
@@ -244,25 +275,27 @@
document.getElementById('loginForm').addEventListener('submit', function(e) {
e.preventDefault();
const gcode = document.getElementById('gcode').value;
const userId = document.getElementById('userId').value;
const password = document.getElementById('password').value;
const rememberMe = document.querySelector('input[type="checkbox"]').checked;
if (!userId || !password) {
showError('사용자 ID비밀번호를 입력해주세요.');
if (!gcode || !userId || !password) {
showError('그룹코드/사용자ID/비밀번호를 입력해주세요.');
return;
}
// 로딩 표시
showLoading();
// HomeController의 로그인 API 호출
// HomeController의 로그인 API 호출
fetch('http://127.0.0.1:9000/Home/Login', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
},
body: JSON.stringify({
Gcode: gcode,
UserId: userId,
Password: password,
RememberMe: rememberMe
@@ -276,6 +309,11 @@
// 로그인 성공
showSuccess(data.Message);
// WebView2에 로그인 성공 메시지 전송
if (window.chrome && window.chrome.webview) {
window.chrome.webview.postMessage('LOGIN_SUCCESS');
}
// 리다이렉트 URL이 있으면 이동
if (data.RedirectUrl) {
setTimeout(() => {
@@ -342,12 +380,103 @@
}, 3000);
}
// 그룹 목록 로드
function loadUserGroups() {
fetch('http://127.0.0.1:9000/DashBoard/GetUserGroups')
.then(response => response.json())
.then(data => {
const gcodeSelect = document.getElementById('gcode');
// 기존 옵션 제거 (첫 번째 옵션 제외)
while (gcodeSelect.children.length > 1) {
gcodeSelect.removeChild(gcodeSelect.lastChild);
}
// 데이터 추가
data.forEach(group => {
if (group.gcode && group.name) {
const option = document.createElement('option');
option.value = group.gcode;
option.textContent = group.name;
option.className = 'text-gray-800';
gcodeSelect.appendChild(option);
}
});
// 이전 로그인 정보 설정
setPreviousLoginInfo();
})
.catch(error => {
console.error('그룹 목록 로드 중 오류 발생:', error);
showError('부서 목록을 불러오는 중 오류가 발생했습니다.');
});
}
// 이전 로그인 정보 설정
function setPreviousLoginInfo() {
// HomeController의 GetPreviousLoginInfo API 호출
fetch('http://127.0.0.1:9000/Home/GetPreviousLoginInfo')
.then(response => response.json())
.then(data => {
if (data.Success && data.Data) {
handlePreviousLoginInfo(data.Data);
}
})
.catch(error => {
console.error('이전 로그인 정보 로드 중 오류 발생:', error);
// 오류가 발생해도 기본 포커스 설정
setTimeout(() => {
document.getElementById('gcode').focus();
}, 100);
});
}
// 이전 로그인 정보 처리
function handlePreviousLoginInfo(data) {
let hasPreviousInfo = false;
if (data && data.Gcode) {
// 부서 선택
const gcodeSelect = document.getElementById('gcode');
gcodeSelect.value = data.Gcode;
// 부서 선택 시 라벨 애니메이션 적용
const label = gcodeSelect.nextElementSibling;
if (label && label.classList.contains('floating-label')) {
label.style.transform = 'translateY(-1.5rem) scale(0.85)';
label.style.color = '#3b82f6';
}
hasPreviousInfo = true;
}
if (data && data.UserId) {
// 사용자 ID 설정
document.getElementById('userId').value = data.UserId;
// 사용자 ID 입력 시 라벨 애니메이션 적용
const userIdInput = document.getElementById('userId');
const label = userIdInput.nextElementSibling;
if (label && label.classList.contains('floating-label')) {
label.style.transform = 'translateY(-1.5rem) scale(0.85)';
label.style.color = '#3b82f6';
}
hasPreviousInfo = true;
}
// 이전 로그인 정보가 있으면 비밀번호 필드에, 없으면 부서 선택에 포커스
setTimeout(() => {
if (hasPreviousInfo) {
document.getElementById('password').focus();
} else {
document.getElementById('gcode').focus();
}
}, 100);
}
// 페이지 로드 시 애니메이션
document.addEventListener('DOMContentLoaded', function() {
// 입력 필드에 자동 포커스
setTimeout(() => {
document.getElementById('userId').focus();
}, 500);
// 그룹 목록 로드
loadUserGroups();
});
</script>
</body>