|
|
|
|
@@ -3,16 +3,17 @@
|
|
|
|
|
*/
|
|
|
|
|
|
|
|
|
|
// API 설정
|
|
|
|
|
const API_BASE = window.API_BASE_URL || 'http://localhost:20005/api';
|
|
|
|
|
const API_BASE = window.API_BASE_URL || 'http://localhost:30005/api';
|
|
|
|
|
|
|
|
|
|
// 상태 변수
|
|
|
|
|
let selectedFactoryId = null;
|
|
|
|
|
let selectedWorkplaceId = null;
|
|
|
|
|
let selectedWorkplaceName = null;
|
|
|
|
|
let selectedType = null; // 'nonconformity' | 'safety'
|
|
|
|
|
let selectedType = null; // 'nonconformity' | 'safety' | 'facility'
|
|
|
|
|
let selectedCategoryId = null;
|
|
|
|
|
let selectedCategoryName = null;
|
|
|
|
|
let selectedItemId = null;
|
|
|
|
|
let customItemName = null;
|
|
|
|
|
let selectedTbmSessionId = null;
|
|
|
|
|
let selectedVisitRequestId = null;
|
|
|
|
|
let photos = [null, null, null, null, null];
|
|
|
|
|
@@ -166,10 +167,9 @@ async function loadMapImage() {
|
|
|
|
|
if (data.success && data.data) {
|
|
|
|
|
const selectedCategory = data.data.find(c => c.category_id == selectedFactoryId);
|
|
|
|
|
if (selectedCategory && selectedCategory.layout_image) {
|
|
|
|
|
const baseUrl = (window.API_BASE_URL || 'http://localhost:20005').replace('/api', '');
|
|
|
|
|
const fullImageUrl = selectedCategory.layout_image.startsWith('http')
|
|
|
|
|
? selectedCategory.layout_image
|
|
|
|
|
: `${baseUrl}${selectedCategory.layout_image}`;
|
|
|
|
|
: selectedCategory.layout_image;
|
|
|
|
|
|
|
|
|
|
canvasImage = new Image();
|
|
|
|
|
canvasImage.onload = () => renderMap();
|
|
|
|
|
@@ -251,7 +251,7 @@ function renderMap() {
|
|
|
|
|
ctx.fillRect(0, 0, canvas.width, canvas.height);
|
|
|
|
|
|
|
|
|
|
// 배치도 이미지
|
|
|
|
|
if (canvasImage && canvasImage.complete) {
|
|
|
|
|
if (canvasImage && canvasImage.complete && canvasImage.naturalWidth > 0) {
|
|
|
|
|
const scale = Math.min(canvas.width / canvasImage.width, canvas.height / canvasImage.height);
|
|
|
|
|
const x = (canvas.width - canvasImage.width * scale) / 2;
|
|
|
|
|
const y = (canvas.height - canvasImage.height * scale) / 2;
|
|
|
|
|
@@ -587,6 +587,14 @@ function renderItems(items) {
|
|
|
|
|
btn.onclick = () => onItemSelect(item, btn);
|
|
|
|
|
grid.appendChild(btn);
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
// 직접 입력 버튼 추가
|
|
|
|
|
const customBtn = document.createElement('button');
|
|
|
|
|
customBtn.type = 'button';
|
|
|
|
|
customBtn.className = 'item-btn custom-input-btn';
|
|
|
|
|
customBtn.textContent = '+ 직접 입력';
|
|
|
|
|
customBtn.onclick = () => showCustomItemInput(customBtn);
|
|
|
|
|
grid.appendChild(customBtn);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
@@ -598,6 +606,21 @@ function onItemSelect(item, btn) {
|
|
|
|
|
btn.classList.add('selected');
|
|
|
|
|
|
|
|
|
|
selectedItemId = item.item_id;
|
|
|
|
|
customItemName = null;
|
|
|
|
|
|
|
|
|
|
// 직접 입력 영역 숨기기
|
|
|
|
|
const customInput = document.getElementById('customItemInput');
|
|
|
|
|
if (customInput) {
|
|
|
|
|
customInput.style.display = 'none';
|
|
|
|
|
document.getElementById('customItemName').value = '';
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 직접 입력 버튼 텍스트 초기화
|
|
|
|
|
const customBtn = document.querySelector('.item-btn.custom-input-btn');
|
|
|
|
|
if (customBtn) {
|
|
|
|
|
customBtn.textContent = '+ 직접 입력';
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
updateStepStatus();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
@@ -667,9 +690,9 @@ function updateStepStatus() {
|
|
|
|
|
steps[2].classList.toggle('active', step2Complete);
|
|
|
|
|
|
|
|
|
|
// Step 3: 항목
|
|
|
|
|
const step3Complete = selectedItemId;
|
|
|
|
|
steps[2].classList.toggle('completed', step3Complete);
|
|
|
|
|
steps[3].classList.toggle('active', step3Complete);
|
|
|
|
|
const step3Complete = selectedItemId || (selectedItemId === 'custom' && customItemName);
|
|
|
|
|
steps[2].classList.toggle('completed', !!step3Complete);
|
|
|
|
|
steps[3].classList.toggle('active', !!step3Complete);
|
|
|
|
|
|
|
|
|
|
// 제출 버튼 활성화
|
|
|
|
|
const submitBtn = document.getElementById('submitBtn');
|
|
|
|
|
@@ -697,7 +720,8 @@ async function submitReport() {
|
|
|
|
|
tbm_session_id: selectedTbmSessionId,
|
|
|
|
|
visit_request_id: selectedVisitRequestId,
|
|
|
|
|
issue_category_id: selectedCategoryId,
|
|
|
|
|
issue_item_id: selectedItemId,
|
|
|
|
|
issue_item_id: selectedItemId === 'custom' ? null : selectedItemId,
|
|
|
|
|
custom_item_name: customItemName || null,
|
|
|
|
|
additional_description: additionalDescription || null,
|
|
|
|
|
photos: photos.filter(p => p !== null)
|
|
|
|
|
};
|
|
|
|
|
@@ -728,6 +752,77 @@ async function submitReport() {
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* 직접 입력 버튼 클릭
|
|
|
|
|
*/
|
|
|
|
|
function showCustomItemInput(btn) {
|
|
|
|
|
// 기존 항목 선택 해제
|
|
|
|
|
document.querySelectorAll('.item-btn').forEach(b => b.classList.remove('selected'));
|
|
|
|
|
btn.classList.add('selected');
|
|
|
|
|
selectedItemId = null;
|
|
|
|
|
customItemName = null;
|
|
|
|
|
|
|
|
|
|
const customInput = document.getElementById('customItemInput');
|
|
|
|
|
if (customInput) {
|
|
|
|
|
customInput.style.display = 'flex';
|
|
|
|
|
document.getElementById('customItemName').focus();
|
|
|
|
|
}
|
|
|
|
|
updateStepStatus();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* 직접 입력 확인
|
|
|
|
|
*/
|
|
|
|
|
function confirmCustomItem() {
|
|
|
|
|
const input = document.getElementById('customItemName');
|
|
|
|
|
const name = input.value.trim();
|
|
|
|
|
if (!name) {
|
|
|
|
|
input.focus();
|
|
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
customItemName = name;
|
|
|
|
|
selectedItemId = 'custom';
|
|
|
|
|
updateStepStatus();
|
|
|
|
|
|
|
|
|
|
// 직접 입력 UI 숨기되 값은 유지
|
|
|
|
|
const customInput = document.getElementById('customItemInput');
|
|
|
|
|
if (customInput) {
|
|
|
|
|
customInput.style.display = 'none';
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 직접 입력 버튼 텍스트 업데이트
|
|
|
|
|
const customBtn = document.querySelector('.item-btn.custom-input-btn');
|
|
|
|
|
if (customBtn) {
|
|
|
|
|
customBtn.textContent = `✓ ${name}`;
|
|
|
|
|
customBtn.classList.add('selected');
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* 직접 입력 취소
|
|
|
|
|
*/
|
|
|
|
|
function cancelCustomItem() {
|
|
|
|
|
const customInput = document.getElementById('customItemInput');
|
|
|
|
|
if (customInput) {
|
|
|
|
|
customInput.style.display = 'none';
|
|
|
|
|
document.getElementById('customItemName').value = '';
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
customItemName = null;
|
|
|
|
|
if (selectedItemId === 'custom') {
|
|
|
|
|
selectedItemId = null;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 직접 입력 버튼 상태 초기화
|
|
|
|
|
const customBtn = document.querySelector('.item-btn.custom-input-btn');
|
|
|
|
|
if (customBtn) {
|
|
|
|
|
customBtn.textContent = '+ 직접 입력';
|
|
|
|
|
customBtn.classList.remove('selected');
|
|
|
|
|
}
|
|
|
|
|
updateStepStatus();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 기타 위치 입력 시 위치 정보 업데이트
|
|
|
|
|
document.addEventListener('DOMContentLoaded', () => {
|
|
|
|
|
const customLocationInput = document.getElementById('customLocation');
|
|
|
|
|
|