166 lines
5.4 KiB
JavaScript
166 lines
5.4 KiB
JavaScript
// ChemiFactory MES - System Settings Frontend Logic
|
|
const API_SETTINGS = "/settings";
|
|
|
|
let allSettings = [];
|
|
|
|
// DOM 준비 상태와 무관하게 theme.js 로딩 완료 대기
|
|
function waitForThemeAndInit() {
|
|
// 최대 2초 동안 AppTheme 대기
|
|
let attempts = 0;
|
|
const maxAttempts = 20; // 100ms * 20 = 2초
|
|
|
|
const checkReady = () => {
|
|
attempts++;
|
|
if (window.AppTheme) {
|
|
// AppTheme 준비 완료, 테마 선택기 초기화
|
|
initThemeSelector();
|
|
} else if (attempts < maxAttempts) {
|
|
// 아직 준비 안 됨, 100ms 후 재시도
|
|
setTimeout(checkReady, 100);
|
|
} else {
|
|
console.warn("[Setting] AppTheme not loaded after 2 seconds");
|
|
}
|
|
};
|
|
|
|
checkReady();
|
|
}
|
|
|
|
document.addEventListener("DOMContentLoaded", () => {
|
|
fetchSettings();
|
|
document.getElementById("settings-form").addEventListener("submit", saveSettings);
|
|
waitForThemeAndInit();
|
|
});
|
|
|
|
// --- 화면 테마 선택기 (theme.js의 전역 AppTheme 사용, 서버 DB와 무관) ---
|
|
function initThemeSelector() {
|
|
const cards = document.querySelectorAll(".theme-option-card");
|
|
if (!cards.length) {
|
|
console.warn("[Theme Selector] No theme option cards found");
|
|
return;
|
|
}
|
|
|
|
if (!window.AppTheme) {
|
|
console.error("[Theme Selector] AppTheme is not available");
|
|
return;
|
|
}
|
|
|
|
// 현재 저장된 테마에 active 표시
|
|
const applyActiveState = (theme) => {
|
|
cards.forEach(card => {
|
|
card.classList.toggle("active", card.dataset.themeValue === theme);
|
|
});
|
|
};
|
|
|
|
// 초기 테마 상태 적용
|
|
const currentTheme = window.AppTheme.get();
|
|
applyActiveState(currentTheme);
|
|
console.log("[Theme Selector] Initialized with theme:", currentTheme);
|
|
|
|
cards.forEach(card => {
|
|
const selectTheme = () => {
|
|
const theme = card.dataset.themeValue;
|
|
console.log("[Theme Selector] User selected theme:", theme);
|
|
window.AppTheme.set(theme); // localStorage 저장 + 즉시 화면 적용
|
|
applyActiveState(theme);
|
|
};
|
|
card.addEventListener("click", selectTheme);
|
|
// 키보드 접근성 (Enter/Space)
|
|
card.addEventListener("keydown", (e) => {
|
|
if (e.key === "Enter" || e.key === " ") {
|
|
e.preventDefault();
|
|
selectTheme();
|
|
}
|
|
});
|
|
});
|
|
}
|
|
|
|
async function fetchSettings() {
|
|
try {
|
|
const res = await fetch(`${API_SETTINGS}/`);
|
|
if (!res.ok) throw new Error("Failed to fetch settings");
|
|
allSettings = await res.json();
|
|
renderSettings(allSettings);
|
|
} catch (err) {
|
|
console.error(err);
|
|
document.getElementById("settings-container").innerHTML = `<div style="color:var(--accent-red); text-align:center; padding:20px 0;">설정 정보를 불러오는 도중 오류가 발생했습니다.</div>`;
|
|
}
|
|
}
|
|
|
|
function renderSettings(settings) {
|
|
const container = document.getElementById("settings-container");
|
|
container.innerHTML = "";
|
|
|
|
// Group settings by category
|
|
const grouped = {};
|
|
settings.forEach(s => {
|
|
if (!grouped[s.setting_group]) {
|
|
grouped[s.setting_group] = [];
|
|
}
|
|
grouped[s.setting_group].push(s);
|
|
});
|
|
|
|
for (const groupName in grouped) {
|
|
// Category Header
|
|
const categoryDiv = document.createElement("div");
|
|
categoryDiv.className = "settings-category";
|
|
categoryDiv.innerText = translateGroup(groupName);
|
|
container.appendChild(categoryDiv);
|
|
|
|
// Inputs mapping
|
|
grouped[groupName].forEach(s => {
|
|
const group = document.createElement("div");
|
|
group.className = "form-group";
|
|
|
|
let inputType = "text";
|
|
if (s.setting_type === "integer" || s.setting_type === "float") {
|
|
inputType = "number";
|
|
}
|
|
|
|
group.innerHTML = `
|
|
<label for="setting-${s.setting_key}">${s.setting_key} (${s.description || "상세 비고 없음"})</label>
|
|
<input type="${inputType}" id="setting-${s.setting_key}" data-key="${s.setting_key}" class="form-control" value="${s.setting_value}">
|
|
<div class="form-desc">타입: ${s.setting_type}</div>
|
|
`;
|
|
container.appendChild(group);
|
|
});
|
|
}
|
|
}
|
|
|
|
function translateGroup(group) {
|
|
const dict = {
|
|
"mqtt": "MQTT 통신 파라미터 설정",
|
|
"gateway": "ESP32 게이트웨이 기기 연동 설정",
|
|
"database": "데이터베이스 연동 세부 설정",
|
|
"system": "시스템 전역 상용 매개변수"
|
|
};
|
|
return dict[group] || group;
|
|
}
|
|
|
|
async function saveSettings(e) {
|
|
e.preventDefault();
|
|
|
|
const payload = [];
|
|
const inputs = document.querySelectorAll("#settings-container input");
|
|
inputs.forEach(input => {
|
|
payload.push({
|
|
setting_key: input.dataset.key,
|
|
setting_value: input.value
|
|
});
|
|
});
|
|
|
|
try {
|
|
const res = await fetch(`${API_SETTINGS}/`, {
|
|
method: "PUT",
|
|
headers: { "Content-Type": "application/json" },
|
|
body: JSON.stringify(payload)
|
|
});
|
|
|
|
if (!res.ok) throw new Error("Saving settings failed");
|
|
alert("시스템 설정 정보가 성공적으로 업데이트되었습니다!");
|
|
fetchSettings();
|
|
} catch (err) {
|
|
console.error(err);
|
|
alert("설정 적용 도중 오류가 발생했습니다.");
|
|
}
|
|
}
|