// Please see documentation at https://docs.microsoft.com/aspnet/core/client-side/bundling-and-minification
// for details on configuring this project to bundle and minify static web assets.
// API Base URL (configured server-side)
const API_BASE_URL = window.API_BASE_URL || '/api';
// Show toast notification
function showToast(message, type = 'info') {
const toastContainer = document.getElementById('toastContainer') || createToastContainer();
const toastId = 'toast-' + Date.now();
const bgClass = {
'success': 'bg-success',
'danger': 'bg-danger',
'warning': 'bg-warning',
'info': 'bg-info',
'error': 'bg-danger'
}[type] || 'bg-info';
const toastHtml = `
`;
toastContainer.insertAdjacentHTML('beforeend', toastHtml);
const toastElement = document.getElementById(toastId);
const toast = new bootstrap.Toast(toastElement, { delay: 3000 });
toast.show();
toastElement.addEventListener('hidden.bs.toast', () => {
toastElement.remove();
});
}
function createToastContainer() {
const container = document.createElement('div');
container.id = 'toastContainer';
container.className = 'toast-container';
document.body.appendChild(container);
return container;
}
// Show loading spinner
function showLoading() {
const existingOverlay = document.getElementById('loadingOverlay');
if (existingOverlay) return;
const overlay = document.createElement('div');
overlay.id = 'loadingOverlay';
overlay.className = 'spinner-overlay';
overlay.innerHTML = `
Loading...
`;
document.body.appendChild(overlay);
}
// Hide loading spinner
function hideLoading() {
const overlay = document.getElementById('loadingOverlay');
if (overlay) {
overlay.remove();
}
}
// API call helper
async function apiCall(url, options = {}) {
const { silent = false, ...fetchOptions } = options;
try {
if (!silent) {
showLoading();
}
const response = await fetch(url, {
...fetchOptions,
headers: {
'Content-Type': 'application/json',
...fetchOptions.headers
}
});
if (!response.ok) {
const errorData = await response.json().catch(() => ({ error: response.statusText }));
throw new Error(errorData.error || `HTTP ${response.status}: ${response.statusText}`);
}
return await response.json();
} catch (error) {
if (!silent) {
showToast(error.message, 'error');
}
throw error;
} finally {
if (!silent) {
hideLoading();
}
}
}
// Format date
function formatDate(dateString) {
if (!dateString) return '-';
const date = new Date(dateString);
return date.toLocaleString('zh-CN', {
year: 'numeric',
month: '2-digit',
day: '2-digit',
hour: '2-digit',
minute: '2-digit',
second: '2-digit'
});
}
// Get status badge class
function getStatusBadgeClass(status) {
const statusMap = {
'Stopped': 'status-stopped',
'Starting': 'status-starting',
'Running': 'status-running',
'Stopping': 'status-stopping',
'Error': 'status-error'
};
return statusMap[status] || 'bg-secondary';
}
// Get status text
function getStatusText(status) {
const statusMap = {
'Stopped': '已停止',
'Starting': '启动中',
'Running': '运行中',
'Stopping': '停止中',
'Error': '错误'
};
return statusMap[status] || status;
}
// Get PLC type text
function getPlcTypeText(plcType) {
const plcTypeMap = {
'S7200Smart': 'S7-200 Smart',
'S71200': 'S7-1200',
'S71500': 'S7-1500',
'S7300': 'S7-300',
'S7400': 'S7-400'
};
return plcTypeMap[plcType] || plcType;
}
// Confirm action
function confirmAction(message, callback) {
if (confirm(message)) {
callback();
}
}
// Redirect with delay
function redirectWithDelay(url, delay = 1500) {
setTimeout(() => {
window.location.href = url;
}, delay);
}
// Format bytes
function formatBytes(bytes, decimals = 2) {
if (bytes === 0) return '0 Bytes';
const k = 1024;
const dm = decimals < 0 ? 0 : decimals;
const sizes = ['Bytes', 'KB', 'MB', 'GB'];
const i = Math.floor(Math.log(bytes) / Math.log(k));
return parseFloat((bytes / Math.pow(k, i)).toFixed(dm)) + ' ' + sizes[i];
}
// Auto-refresh interval handler
let refreshInterval = null;
function startAutoRefresh(callback, intervalMs = 5000) {
stopAutoRefresh();
callback(); // Initial call
refreshInterval = setInterval(callback, intervalMs);
}
function stopAutoRefresh() {
if (refreshInterval) {
clearInterval(refreshInterval);
refreshInterval = null;
}
}
// Page unload handler
window.addEventListener('beforeunload', () => {
stopAutoRefresh();
});