"Update templates for improved UI/UX"
This commit is contained in:
parent
731a9fe6f1
commit
ef8b5bf177
@ -1418,6 +1418,12 @@ def jobs_page():
|
|||||||
"""Zeigt die Übersichtsseite für Druckaufträge an."""
|
"""Zeigt die Übersichtsseite für Druckaufträge an."""
|
||||||
return render_template("jobs.html")
|
return render_template("jobs.html")
|
||||||
|
|
||||||
|
@app.route("/jobs/new")
|
||||||
|
@login_required
|
||||||
|
def new_job_page():
|
||||||
|
"""Zeigt die Seite zum Erstellen neuer Druckaufträge an."""
|
||||||
|
return render_template("jobs.html")
|
||||||
|
|
||||||
@app.route("/stats")
|
@app.route("/stats")
|
||||||
@login_required
|
@login_required
|
||||||
def stats_page():
|
def stats_page():
|
||||||
@ -4343,19 +4349,19 @@ if __name__ == "__main__":
|
|||||||
ssl_context = get_ssl_context()
|
ssl_context = get_ssl_context()
|
||||||
|
|
||||||
if ssl_context:
|
if ssl_context:
|
||||||
app_logger.info("Starte HTTPS-Server auf 0.0.0.0:8443")
|
app_logger.info("Starte HTTPS-Server auf 0.0.0.0:443")
|
||||||
app.run(
|
app.run(
|
||||||
host="0.0.0.0",
|
host="0.0.0.0",
|
||||||
port=8443,
|
port=443,
|
||||||
debug=False,
|
debug=False,
|
||||||
ssl_context=ssl_context,
|
ssl_context=ssl_context,
|
||||||
threaded=True
|
threaded=True
|
||||||
)
|
)
|
||||||
else:
|
else:
|
||||||
app_logger.info("Starte HTTP-Server auf 0.0.0.0:8080")
|
app_logger.info("Starte HTTP-Server auf 0.0.0.0:80")
|
||||||
app.run(
|
app.run(
|
||||||
host="0.0.0.0",
|
host="0.0.0.0",
|
||||||
port=8080,
|
port=80,
|
||||||
debug=False,
|
debug=False,
|
||||||
threaded=True
|
threaded=True
|
||||||
)
|
)
|
||||||
@ -4371,9 +4377,3 @@ if __name__ == "__main__":
|
|||||||
except:
|
except:
|
||||||
pass
|
pass
|
||||||
sys.exit(1)
|
sys.exit(1)
|
||||||
|
|
||||||
try:
|
|
||||||
stop_queue_manager()
|
|
||||||
except:
|
|
||||||
pass
|
|
||||||
sys.exit(1)
|
|
||||||
|
@ -769,4 +769,5 @@ document.addEventListener('DOMContentLoaded', function() {
|
|||||||
};
|
};
|
||||||
});
|
});
|
||||||
</script>
|
</script>
|
||||||
|
{% endblock %}
|
||||||
{% endblock %}
|
{% endblock %}
|
@ -518,9 +518,9 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
setupEventListeners() {
|
setupEventListeners() {
|
||||||
// Refresh Button
|
// Refresh Button
|
||||||
const refreshBtn = document.getElementById('refreshDashboard');
|
const refreshBtn = document.getElementById('refreshDashboard');
|
||||||
if (refreshBtn) {
|
if (refreshBtn) {
|
||||||
refreshBtn.addEventListener('click', () => {
|
refreshBtn.addEventListener('click', () => {
|
||||||
this.refreshDashboard();
|
this.refreshDashboard();
|
||||||
});
|
});
|
||||||
|
@ -32,55 +32,7 @@
|
|||||||
}
|
}
|
||||||
.focus\:border-mercedes-blue:focus { border-color: #0073ce; }
|
.focus\:border-mercedes-blue:focus { border-color: #0073ce; }
|
||||||
|
|
||||||
/* Enhanced Page Header */
|
/* Enhanced Form Elements */
|
||||||
.guest-header {
|
|
||||||
background: linear-gradient(135deg, #ffffff 0%, #f8fafc 100%);
|
|
||||||
border: 1px solid #e2e8f0;
|
|
||||||
box-shadow:
|
|
||||||
0 10px 25px -5px rgba(0, 0, 0, 0.1),
|
|
||||||
0 4px 6px -2px rgba(0, 0, 0, 0.05);
|
|
||||||
position: relative;
|
|
||||||
overflow: hidden;
|
|
||||||
}
|
|
||||||
|
|
||||||
.dark .guest-header {
|
|
||||||
background: linear-gradient(135deg, #1e293b 0%, #0f172a 100%);
|
|
||||||
border-color: #334155;
|
|
||||||
}
|
|
||||||
|
|
||||||
.guest-header::before {
|
|
||||||
content: '';
|
|
||||||
position: absolute;
|
|
||||||
top: 0;
|
|
||||||
left: -100%;
|
|
||||||
width: 100%;
|
|
||||||
height: 100%;
|
|
||||||
background: linear-gradient(90deg, transparent, rgba(0, 115, 206, 0.1), transparent);
|
|
||||||
transition: left 0.5s;
|
|
||||||
}
|
|
||||||
|
|
||||||
.guest-header:hover::before {
|
|
||||||
left: 100%;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Enhanced Form Container */
|
|
||||||
.guest-form-container {
|
|
||||||
background: linear-gradient(135deg, #ffffff 0%, #f8fafc 100%);
|
|
||||||
border: 1px solid #e2e8f0;
|
|
||||||
box-shadow:
|
|
||||||
0 20px 40px -12px rgba(0, 0, 0, 0.1),
|
|
||||||
0 8px 16px -4px rgba(0, 0, 0, 0.05);
|
|
||||||
border-radius: 16px;
|
|
||||||
position: relative;
|
|
||||||
overflow: hidden;
|
|
||||||
}
|
|
||||||
|
|
||||||
.dark .guest-form-container {
|
|
||||||
background: linear-gradient(135deg, #1e293b 0%, #0f172a 100%);
|
|
||||||
border-color: #334155;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Enhanced Form Inputs */
|
|
||||||
.mercedes-form-input {
|
.mercedes-form-input {
|
||||||
transition: all 0.2s ease;
|
transition: all 0.2s ease;
|
||||||
border: 1px solid #d1d5db;
|
border: 1px solid #d1d5db;
|
||||||
@ -166,100 +118,6 @@
|
|||||||
75% { transform: translateX(5px); }
|
75% { transform: translateX(5px); }
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Enhanced Info Banner */
|
|
||||||
.info-banner {
|
|
||||||
background: linear-gradient(135deg, #eff6ff 0%, #dbeafe 100%);
|
|
||||||
border: 1px solid #bfdbfe;
|
|
||||||
border-radius: 12px;
|
|
||||||
position: relative;
|
|
||||||
overflow: hidden;
|
|
||||||
}
|
|
||||||
|
|
||||||
.dark .info-banner {
|
|
||||||
background: linear-gradient(135deg, #1e3a8a 0%, #1e40af 100%);
|
|
||||||
border-color: #3b82f6;
|
|
||||||
}
|
|
||||||
|
|
||||||
.info-banner::before {
|
|
||||||
content: '';
|
|
||||||
position: absolute;
|
|
||||||
top: 0;
|
|
||||||
left: 0;
|
|
||||||
width: 4px;
|
|
||||||
height: 100%;
|
|
||||||
background: linear-gradient(180deg, #3b82f6, #1d4ed8);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Enhanced Buttons */
|
|
||||||
.btn-primary {
|
|
||||||
background: linear-gradient(135deg, #0073ce 0%, #1e40af 100%);
|
|
||||||
border: none;
|
|
||||||
color: white;
|
|
||||||
padding: 0.75rem 2rem;
|
|
||||||
border-radius: 12px;
|
|
||||||
font-weight: 600;
|
|
||||||
text-transform: uppercase;
|
|
||||||
letter-spacing: 0.5px;
|
|
||||||
transition: all 0.3s ease;
|
|
||||||
position: relative;
|
|
||||||
overflow: hidden;
|
|
||||||
display: inline-flex;
|
|
||||||
align-items: center;
|
|
||||||
text-decoration: none;
|
|
||||||
box-shadow: 0 4px 14px 0 rgba(0, 115, 206, 0.39);
|
|
||||||
}
|
|
||||||
|
|
||||||
.btn-primary::before {
|
|
||||||
content: '';
|
|
||||||
position: absolute;
|
|
||||||
top: 0;
|
|
||||||
left: -100%;
|
|
||||||
width: 100%;
|
|
||||||
height: 100%;
|
|
||||||
background: linear-gradient(90deg, transparent, rgba(255, 255, 255, 0.2), transparent);
|
|
||||||
transition: left 0.5s;
|
|
||||||
}
|
|
||||||
|
|
||||||
.btn-primary:hover::before {
|
|
||||||
left: 100%;
|
|
||||||
}
|
|
||||||
|
|
||||||
.btn-primary:hover {
|
|
||||||
transform: translateY(-2px);
|
|
||||||
box-shadow: 0 8px 25px 0 rgba(0, 115, 206, 0.5);
|
|
||||||
}
|
|
||||||
|
|
||||||
.btn-secondary {
|
|
||||||
background: transparent;
|
|
||||||
border: 2px solid #0073ce;
|
|
||||||
color: #0073ce;
|
|
||||||
padding: 0.75rem 2rem;
|
|
||||||
border-radius: 12px;
|
|
||||||
font-weight: 600;
|
|
||||||
text-transform: uppercase;
|
|
||||||
letter-spacing: 0.5px;
|
|
||||||
transition: all 0.3s ease;
|
|
||||||
display: inline-flex;
|
|
||||||
align-items: center;
|
|
||||||
text-decoration: none;
|
|
||||||
}
|
|
||||||
|
|
||||||
.btn-secondary:hover {
|
|
||||||
background: #0073ce;
|
|
||||||
color: white;
|
|
||||||
transform: translateY(-2px);
|
|
||||||
}
|
|
||||||
|
|
||||||
.dark .btn-secondary {
|
|
||||||
border-color: #60a5fa;
|
|
||||||
color: #60a5fa;
|
|
||||||
}
|
|
||||||
|
|
||||||
.dark .btn-secondary:hover {
|
|
||||||
background: #60a5fa;
|
|
||||||
color: #1e293b;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Progress Indicators */
|
/* Progress Indicators */
|
||||||
.progress-step {
|
.progress-step {
|
||||||
background: linear-gradient(135deg, #f3f4f6 0%, #e5e7eb 100%);
|
background: linear-gradient(135deg, #f3f4f6 0%, #e5e7eb 100%);
|
||||||
@ -329,24 +187,6 @@
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Responsive Design */
|
|
||||||
@media (max-width: 768px) {
|
|
||||||
.guest-form-container {
|
|
||||||
margin: 1rem;
|
|
||||||
padding: 1.5rem !important;
|
|
||||||
}
|
|
||||||
|
|
||||||
.btn-primary,
|
|
||||||
.btn-secondary {
|
|
||||||
width: 100%;
|
|
||||||
justify-content: center;
|
|
||||||
}
|
|
||||||
|
|
||||||
.upload-area {
|
|
||||||
height: 120px;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Success Animation */
|
/* Success Animation */
|
||||||
.success-checkmark {
|
.success-checkmark {
|
||||||
animation: checkmark 0.6s ease-in-out;
|
animation: checkmark 0.6s ease-in-out;
|
||||||
@ -367,6 +207,23 @@
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Responsive Design */
|
||||||
|
@media (max-width: 768px) {
|
||||||
|
.dashboard-card {
|
||||||
|
padding: 1rem !important;
|
||||||
|
}
|
||||||
|
|
||||||
|
.btn-primary,
|
||||||
|
.btn-secondary {
|
||||||
|
width: 100%;
|
||||||
|
justify-content: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
.upload-area {
|
||||||
|
height: 120px;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/* Accessibility Enhancements */
|
/* Accessibility Enhancements */
|
||||||
@media (prefers-reduced-motion: reduce) {
|
@media (prefers-reduced-motion: reduce) {
|
||||||
*, *::before, *::after {
|
*, *::before, *::after {
|
||||||
@ -382,74 +239,54 @@
|
|||||||
outline: 2px solid #0073ce;
|
outline: 2px solid #0073ce;
|
||||||
outline-offset: 2px;
|
outline-offset: 2px;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Custom Scrollbar */
|
|
||||||
.custom-scroll::-webkit-scrollbar {
|
|
||||||
width: 6px;
|
|
||||||
}
|
|
||||||
|
|
||||||
.custom-scroll::-webkit-scrollbar-track {
|
|
||||||
background: #f1f5f9;
|
|
||||||
border-radius: 3px;
|
|
||||||
}
|
|
||||||
|
|
||||||
.custom-scroll::-webkit-scrollbar-thumb {
|
|
||||||
background: #0073ce;
|
|
||||||
border-radius: 3px;
|
|
||||||
}
|
|
||||||
|
|
||||||
.custom-scroll::-webkit-scrollbar-thumb:hover {
|
|
||||||
background: #1e40af;
|
|
||||||
}
|
|
||||||
</style>
|
</style>
|
||||||
{% endblock %}
|
{% endblock %}
|
||||||
|
|
||||||
{% block content %}
|
{% block content %}
|
||||||
<div class="space-y-8">
|
<div class="space-y-8">
|
||||||
<!-- Enhanced Page Header -->
|
<!-- Enhanced Page Header -->
|
||||||
<div class="guest-header p-6 rounded-xl relative">
|
<div class="dashboard-card p-6">
|
||||||
<div class="relative z-10">
|
<div class="flex flex-col md:flex-row md:items-center md:justify-between gap-6">
|
||||||
<div class="flex flex-col md:flex-row md:items-center md:justify-between gap-6">
|
<div class="flex items-center gap-6">
|
||||||
<div class="flex items-center gap-4">
|
<div class="w-16 h-16 flex-shrink-0 bg-mercedes-blue text-white rounded-xl flex items-center justify-center">
|
||||||
<div class="w-16 h-16 flex-shrink-0 bg-mercedes-blue text-white rounded-xl flex items-center justify-center">
|
<svg class="w-8 h-8" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
<svg class="w-8 h-8" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M16 7a4 4 0 11-8 0 4 4 0 018 0zM12 14a7 7 0 00-7 7h14a7 7 0 00-7-7z"/>
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M16 7a4 4 0 11-8 0 4 4 0 018 0zM12 14a7 7 0 00-7 7h14a7 7 0 00-7-7z"/>
|
</svg>
|
||||||
|
</div>
|
||||||
|
<div>
|
||||||
|
<h1 class="text-4xl font-bold text-mercedes-black dark:text-white tracking-tight">Gastanfrage</h1>
|
||||||
|
<p class="text-mercedes-gray dark:text-slate-400 mt-1 text-lg">Stellen Sie Ihre 3D-Druckauftrag Anfrage mit Mercedes-Benz Qualitätsstandards</p>
|
||||||
|
<div class="flex items-center mt-2 text-sm text-mercedes-blue">
|
||||||
|
<svg class="w-4 h-4 mr-1" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 8v4l3 3m6-3a9 9 0 11-18 0 9 9 0 0118 0z"/>
|
||||||
</svg>
|
</svg>
|
||||||
</div>
|
<span>Bearbeitungszeit: 24-48 Stunden</span>
|
||||||
<div>
|
|
||||||
<h1 class="text-4xl font-bold text-mercedes-black dark:text-white tracking-tight">Gastanfrage</h1>
|
|
||||||
<p class="text-mercedes-gray dark:text-slate-400 mt-1 text-lg">Stellen Sie Ihre 3D-Druckauftrag Anfrage</p>
|
|
||||||
<div class="flex items-center mt-2 text-sm text-mercedes-blue">
|
|
||||||
<svg class="w-4 h-4 mr-1" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 8v4l3 3m6-3a9 9 0 11-18 0 9 9 0 0118 0z"/>
|
|
||||||
</svg>
|
|
||||||
Bearbeitungszeit: 24-48 Stunden
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="flex flex-wrap gap-3">
|
</div>
|
||||||
<a href="{{ url_for('guest.guest_requests_overview') if url_for else '/guest/requests' }}"
|
<div class="flex flex-wrap gap-3">
|
||||||
class="btn-secondary flex items-center gap-2">
|
<a href="{{ url_for('guest.guest_requests_overview') if url_for else '/guest/requests' }}"
|
||||||
<svg class="w-5 h-5" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
class="btn-secondary flex items-center gap-2">
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M9 12h6m-6 4h6m2 5H7a2 2 0 01-2-2V5a2 2 0 012-2h5.586a1 1 0 01.707.293l5.414 5.414a1 1 0 01.293.707V19a2 2 0 01-2 2z"/>
|
<svg class="w-5 h-5" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
</svg>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M9 12h6m-6 4h6m2 5H7a2 2 0 01-2-2V5a2 2 0 012-2h5.586a1 1 0 01.707.293l5.414 5.414a1 1 0 01.293.707V19a2 2 0 01-2 2z"/>
|
||||||
<span>Anträge Übersicht</span>
|
</svg>
|
||||||
</a>
|
<span>Anträge Übersicht</span>
|
||||||
<a href="{{ url_for('index') if url_for else '/' }}"
|
</a>
|
||||||
class="btn-secondary flex items-center gap-2">
|
<a href="{{ url_for('index') if url_for else '/' }}"
|
||||||
<svg class="w-5 h-5" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
class="btn-secondary flex items-center gap-2">
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M3 12l2-2m0 0l7-7 7 7M5 10v10a1 1 0 001 1h3m10-11l2 2m-2-2v10a1 1 0 01-1 1h-3m-6 0a1 1 0 001-1v-4a1 1 0 011-1h2a1 1 0 011 1v4a1 1 0 001 1m-6 0h6"/>
|
<svg class="w-5 h-5" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
</svg>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M3 12l2-2m0 0l7-7 7 7M5 10v10a1 1 0 001 1h3m10-11l2 2m-2-2v10a1 1 0 01-1 1h-3m-6 0a1 1 0 001-1v-4a1 1 0 011-1h2a1 1 0 011 1v4a1 1 0 001 1m-6 0h6"/>
|
||||||
<span>Startseite</span>
|
</svg>
|
||||||
</a>
|
<span>Startseite</span>
|
||||||
</div>
|
</a>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- Progress Indicator -->
|
<!-- Progress Indicator -->
|
||||||
<div class="guest-form-container p-6">
|
<div class="dashboard-card p-6">
|
||||||
<div class="mb-8">
|
<div class="mb-8">
|
||||||
|
<h2 class="text-lg font-semibold text-mercedes-black dark:text-white mb-4">Antrags-Fortschritt</h2>
|
||||||
<div class="flex items-center justify-between max-w-md mx-auto">
|
<div class="flex items-center justify-between max-w-md mx-auto">
|
||||||
<div class="flex items-center">
|
<div class="flex items-center">
|
||||||
<div class="progress-step active">1</div>
|
<div class="progress-step active">1</div>
|
||||||
@ -472,8 +309,8 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- Enhanced Info Banner -->
|
<!-- Enhanced Info Banner -->
|
||||||
<div class="info-banner p-6 relative">
|
<div class="dashboard-card p-6">
|
||||||
<div class="flex items-start gap-4 relative z-10">
|
<div class="flex items-start gap-4">
|
||||||
<div class="w-12 h-12 bg-blue-500 text-white rounded-xl flex items-center justify-center flex-shrink-0">
|
<div class="w-12 h-12 bg-blue-500 text-white rounded-xl flex items-center justify-center flex-shrink-0">
|
||||||
<svg class="h-6 w-6" fill="currentColor" viewBox="0 0 20 20">
|
<svg class="h-6 w-6" fill="currentColor" viewBox="0 0 20 20">
|
||||||
<path fill-rule="evenodd" d="M18 10a8 8 0 11-16 0 8 8 0 0116 0zm-7-4a1 1 0 11-2 0 1 1 0 012 0zM9 9a1 1 0 000 2v3a1 1 0 001 1h1a1 1 0 100-2v-3a1 1 0 00-1-1H9z" clip-rule="evenodd"/>
|
<path fill-rule="evenodd" d="M18 10a8 8 0 11-16 0 8 8 0 0116 0zm-7-4a1 1 0 11-2 0 1 1 0 012 0zM9 9a1 1 0 000 2v3a1 1 0 001 1h1a1 1 0 100-2v-3a1 1 0 00-1-1H9z" clip-rule="evenodd"/>
|
||||||
@ -498,15 +335,15 @@
|
|||||||
</div>
|
</div>
|
||||||
<div class="flex items-center">
|
<div class="flex items-center">
|
||||||
<svg class="w-5 h-5 mr-2 text-green-600" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
<svg class="w-5 h-5 mr-2 text-green-600" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M3 8l7.89 2.26a2 2 0 001.22 0L21 8M5 19h14a2 2 0 002-2V7a2 2 0 00-2-2H5a2 2 0 00-2 2v10a2 2 0 002 2z"/>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M9 12l2 2 4-4m6 2a9 9 0 11-18 0 9 9 0 0118 0z"/>
|
||||||
</svg>
|
</svg>
|
||||||
<span>E-Mail-Benachrichtigung über Status</span>
|
<span>Professionelle 3D-Druck-Qualität</span>
|
||||||
</div>
|
</div>
|
||||||
<div class="flex items-center">
|
<div class="flex items-center">
|
||||||
<svg class="w-5 h-5 mr-2 text-green-600" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
<svg class="w-5 h-5 mr-2 text-green-600" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M9 12l2 2 4-4m6 2a9 9 0 11-18 0 9 9 0 0118 0z"/>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M13 10V3L4 14h7v7l9-11h-7z"/>
|
||||||
</svg>
|
</svg>
|
||||||
<span>Automatischer Druckstart nach Genehmigung</span>
|
<span>Kostenlose Beratung inklusive</span>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@ -514,7 +351,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- Enhanced Form Container -->
|
<!-- Enhanced Form Container -->
|
||||||
<div class="guest-form-container p-8">
|
<div class="dashboard-card p-8">
|
||||||
<div class="mb-8">
|
<div class="mb-8">
|
||||||
<h2 class="text-2xl font-bold text-mercedes-black dark:text-white mb-3">
|
<h2 class="text-2xl font-bold text-mercedes-black dark:text-white mb-3">
|
||||||
Druckantrag einreichen
|
Druckantrag einreichen
|
||||||
@ -536,10 +373,10 @@
|
|||||||
</svg>
|
</svg>
|
||||||
Persönliche Angaben
|
Persönliche Angaben
|
||||||
</h3>
|
</h3>
|
||||||
|
|
||||||
<div class="grid grid-cols-1 md:grid-cols-2 gap-6">
|
<div class="grid grid-cols-1 md:grid-cols-2 gap-6">
|
||||||
<!-- Name -->
|
<!-- Name -->
|
||||||
<div>
|
<div>
|
||||||
<label for="{{ form.name.id if form else 'name' }}" class="block text-sm font-medium text-mercedes-black dark:text-slate-300 mb-2">
|
<label for="{{ form.name.id if form else 'name' }}" class="block text-sm font-medium text-mercedes-black dark:text-slate-300 mb-2">
|
||||||
Vollständiger Name *
|
Vollständiger Name *
|
||||||
</label>
|
</label>
|
||||||
@ -552,20 +389,20 @@
|
|||||||
{% endif %}
|
{% endif %}
|
||||||
{% if form and form.name.errors %}
|
{% if form and form.name.errors %}
|
||||||
<div class="mt-2 text-sm text-mercedes-red">
|
<div class="mt-2 text-sm text-mercedes-red">
|
||||||
{% for error in form.name.errors %}
|
{% for error in form.name.errors %}
|
||||||
<p class="flex items-center">
|
<p class="flex items-center">
|
||||||
<svg class="w-4 h-4 mr-1" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
<svg class="w-4 h-4 mr-1" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 8v4m0 4h.01M21 12a9 9 0 11-18 0 9 9 0 0118 0z"/>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 8v4m0 4h.01M21 12a9 9 0 11-18 0 9 9 0 0118 0z"/>
|
||||||
</svg>
|
</svg>
|
||||||
{{ error }}
|
{{ error }}
|
||||||
</p>
|
</p>
|
||||||
{% endfor %}
|
{% endfor %}
|
||||||
</div>
|
</div>
|
||||||
{% endif %}
|
{% endif %}
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- E-Mail -->
|
<!-- E-Mail -->
|
||||||
<div>
|
<div>
|
||||||
<label for="{{ form.email.id if form else 'email' }}" class="block text-sm font-medium text-mercedes-black dark:text-slate-300 mb-2">
|
<label for="{{ form.email.id if form else 'email' }}" class="block text-sm font-medium text-mercedes-black dark:text-slate-300 mb-2">
|
||||||
E-Mail-Adresse *
|
E-Mail-Adresse *
|
||||||
</label>
|
</label>
|
||||||
@ -581,16 +418,16 @@
|
|||||||
</p>
|
</p>
|
||||||
{% if form and form.email.errors %}
|
{% if form and form.email.errors %}
|
||||||
<div class="mt-2 text-sm text-mercedes-red">
|
<div class="mt-2 text-sm text-mercedes-red">
|
||||||
{% for error in form.email.errors %}
|
{% for error in form.email.errors %}
|
||||||
<p class="flex items-center">
|
<p class="flex items-center">
|
||||||
<svg class="w-4 h-4 mr-1" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
<svg class="w-4 h-4 mr-1" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 8v4m0 4h.01M21 12a9 9 0 11-18 0 9 9 0 0118 0z"/>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 8v4m0 4h.01M21 12a9 9 0 11-18 0 9 9 0 0118 0z"/>
|
||||||
</svg>
|
</svg>
|
||||||
{{ error }}
|
{{ error }}
|
||||||
</p>
|
</p>
|
||||||
{% endfor %}
|
{% endfor %}
|
||||||
</div>
|
</div>
|
||||||
{% endif %}
|
{% endif %}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@ -603,10 +440,10 @@
|
|||||||
</svg>
|
</svg>
|
||||||
Projekt-Details
|
Projekt-Details
|
||||||
</h3>
|
</h3>
|
||||||
|
|
||||||
<div class="grid grid-cols-1 md:grid-cols-2 gap-6">
|
<div class="grid grid-cols-1 md:grid-cols-2 gap-6">
|
||||||
<!-- Drucker -->
|
<!-- Drucker -->
|
||||||
<div>
|
<div>
|
||||||
<label for="{{ form.printer_id.id if form else 'printer_id' }}" class="block text-sm font-medium text-mercedes-black dark:text-slate-300 mb-2">
|
<label for="{{ form.printer_id.id if form else 'printer_id' }}" class="block text-sm font-medium text-mercedes-black dark:text-slate-300 mb-2">
|
||||||
Gewünschter Drucker *
|
Gewünschter Drucker *
|
||||||
</label>
|
</label>
|
||||||
@ -625,24 +462,24 @@
|
|||||||
</p>
|
</p>
|
||||||
{% if form and form.printer_id.errors %}
|
{% if form and form.printer_id.errors %}
|
||||||
<div class="mt-2 text-sm text-mercedes-red">
|
<div class="mt-2 text-sm text-mercedes-red">
|
||||||
{% for error in form.printer_id.errors %}
|
{% for error in form.printer_id.errors %}
|
||||||
<p class="flex items-center">
|
<p class="flex items-center">
|
||||||
<svg class="w-4 h-4 mr-1" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
<svg class="w-4 h-4 mr-1" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 8v4m0 4h.01M21 12a9 9 0 11-18 0 9 9 0 0118 0z"/>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 8v4m0 4h.01M21 12a9 9 0 11-18 0 9 9 0 0118 0z"/>
|
||||||
</svg>
|
</svg>
|
||||||
{{ error }}
|
{{ error }}
|
||||||
</p>
|
</p>
|
||||||
{% endfor %}
|
{% endfor %}
|
||||||
</div>
|
</div>
|
||||||
{% endif %}
|
{% endif %}
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- Geschätzte Dauer -->
|
<!-- Geschätzte Dauer -->
|
||||||
<div>
|
<div>
|
||||||
<label for="{{ form.duration_min.id if form else 'duration_min' }}" class="block text-sm font-medium text-mercedes-black dark:text-slate-300 mb-2">
|
<label for="{{ form.duration_min.id if form else 'duration_min' }}" class="block text-sm font-medium text-mercedes-black dark:text-slate-300 mb-2">
|
||||||
Geschätzte Druckdauer *
|
Geschätzte Druckdauer *
|
||||||
</label>
|
</label>
|
||||||
<div class="relative">
|
<div class="relative">
|
||||||
{% if form %}
|
{% if form %}
|
||||||
{{ form.duration_min(class="mercedes-form-input block w-full px-4 py-3 pr-20", placeholder="z.B. 120", required="required") }}
|
{{ form.duration_min(class="mercedes-form-input block w-full px-4 py-3 pr-20", placeholder="z.B. 120", required="required") }}
|
||||||
{% else %}
|
{% else %}
|
||||||
@ -652,27 +489,27 @@
|
|||||||
{% endif %}
|
{% endif %}
|
||||||
<div class="absolute inset-y-0 right-0 flex items-center pr-4 pointer-events-none">
|
<div class="absolute inset-y-0 right-0 flex items-center pr-4 pointer-events-none">
|
||||||
<span class="text-mercedes-gray dark:text-slate-400 text-sm font-medium">Minuten</span>
|
<span class="text-mercedes-gray dark:text-slate-400 text-sm font-medium">Minuten</span>
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
<p class="mt-1 text-xs text-mercedes-gray dark:text-slate-400">
|
<p class="mt-1 text-xs text-mercedes-gray dark:text-slate-400">
|
||||||
Ungefähre Druckzeit basierend auf der Dateigröße und Komplexität
|
Ungefähre Druckzeit basierend auf der Dateigröße und Komplexität
|
||||||
</p>
|
</p>
|
||||||
{% if form and form.duration_min.errors %}
|
{% if form and form.duration_min.errors %}
|
||||||
<div class="mt-2 text-sm text-mercedes-red">
|
<div class="mt-2 text-sm text-mercedes-red">
|
||||||
{% for error in form.duration_min.errors %}
|
{% for error in form.duration_min.errors %}
|
||||||
<p class="flex items-center">
|
<p class="flex items-center">
|
||||||
<svg class="w-4 h-4 mr-1" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
<svg class="w-4 h-4 mr-1" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 8v4m0 4h.01M21 12a9 9 0 11-18 0 9 9 0 0118 0z"/>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 8v4m0 4h.01M21 12a9 9 0 11-18 0 9 9 0 0118 0z"/>
|
||||||
</svg>
|
</svg>
|
||||||
{{ error }}
|
{{ error }}
|
||||||
</p>
|
</p>
|
||||||
{% endfor %}
|
{% endfor %}
|
||||||
</div>
|
</div>
|
||||||
{% endif %}
|
{% endif %}
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<!-- Projektbeschreibung -->
|
<!-- Projektbeschreibung -->
|
||||||
<div class="mt-6">
|
<div class="mt-6">
|
||||||
<label for="{{ form.reason.id if form else 'reason' }}" class="block text-sm font-medium text-mercedes-black dark:text-slate-300 mb-2">
|
<label for="{{ form.reason.id if form else 'reason' }}" class="block text-sm font-medium text-mercedes-black dark:text-slate-300 mb-2">
|
||||||
Projektbeschreibung *
|
Projektbeschreibung *
|
||||||
@ -689,16 +526,16 @@
|
|||||||
</p>
|
</p>
|
||||||
{% if form and form.reason.errors %}
|
{% if form and form.reason.errors %}
|
||||||
<div class="mt-2 text-sm text-mercedes-red">
|
<div class="mt-2 text-sm text-mercedes-red">
|
||||||
{% for error in form.reason.errors %}
|
{% for error in form.reason.errors %}
|
||||||
<p class="flex items-center">
|
<p class="flex items-center">
|
||||||
<svg class="w-4 h-4 mr-1" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
<svg class="w-4 h-4 mr-1" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 8v4m0 4h.01M21 12a9 9 0 11-18 0 9 9 0 0118 0z"/>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 8v4m0 4h.01M21 12a9 9 0 11-18 0 9 9 0 0118 0z"/>
|
||||||
</svg>
|
</svg>
|
||||||
{{ error }}
|
{{ error }}
|
||||||
</p>
|
</p>
|
||||||
{% endfor %}
|
{% endfor %}
|
||||||
</div>
|
</div>
|
||||||
{% endif %}
|
{% endif %}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
@ -706,8 +543,8 @@
|
|||||||
<div class="bg-gray-50 dark:bg-slate-800/50 rounded-xl p-6">
|
<div class="bg-gray-50 dark:bg-slate-800/50 rounded-xl p-6">
|
||||||
<h3 class="text-lg font-semibold text-mercedes-black dark:text-white mb-4 flex items-center">
|
<h3 class="text-lg font-semibold text-mercedes-black dark:text-white mb-4 flex items-center">
|
||||||
<svg class="w-5 h-5 mr-2 text-mercedes-blue" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
<svg class="w-5 h-5 mr-2 text-mercedes-blue" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M7 16a4 4 0 01-.88-7.903A5 5 0 1115.9 6L16 6a5 5 0 011 9.9M15 13l-3-3m0 0l-3 3m3-3v12"/>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M7 16a4 4 0 01-.88-7.903A5 5 0 1115.9 6L16 6a5 5 0 011 9.9M15 13l-3-3m0 0l-3 3m3-3v12"/>
|
||||||
</svg>
|
</svg>
|
||||||
3D-Datei hochladen
|
3D-Datei hochladen
|
||||||
</h3>
|
</h3>
|
||||||
|
|
||||||
@ -728,8 +565,8 @@
|
|||||||
<span class="px-2 py-1 bg-mercedes-blue text-white rounded">OBJ</span>
|
<span class="px-2 py-1 bg-mercedes-blue text-white rounded">OBJ</span>
|
||||||
<span class="px-2 py-1 bg-mercedes-blue text-white rounded">3MF</span>
|
<span class="px-2 py-1 bg-mercedes-blue text-white rounded">3MF</span>
|
||||||
<span class="px-2 py-1 bg-mercedes-blue text-white rounded">GCODE</span>
|
<span class="px-2 py-1 bg-mercedes-blue text-white rounded">GCODE</span>
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
{% if form %}
|
{% if form %}
|
||||||
{{ form.file(class="hidden", id="file-input") }}
|
{{ form.file(class="hidden", id="file-input") }}
|
||||||
{% else %}
|
{% else %}
|
||||||
@ -780,21 +617,21 @@
|
|||||||
<button type="submit" id="submit-button"
|
<button type="submit" id="submit-button"
|
||||||
class="btn-primary" disabled>
|
class="btn-primary" disabled>
|
||||||
<svg class="w-5 h-5 mr-2" id="submit-icon" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
<svg class="w-5 h-5 mr-2" id="submit-icon" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 19l9 2-9-18-9 18 9-2zm0 0v-8"/>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 19l9 2-9-18-9 18 9-2zm0 0v-8"/>
|
||||||
</svg>
|
</svg>
|
||||||
<svg class="w-5 h-5 mr-2 animate-spin hidden" id="submit-spinner" fill="none" viewBox="0 0 24 24" stroke="currentColor">
|
<svg class="w-5 h-5 mr-2 animate-spin hidden" id="submit-spinner" fill="none" viewBox="0 0 24 24" stroke="currentColor">
|
||||||
<circle class="opacity-25" cx="12" cy="12" r="10" stroke="currentColor" stroke-width="4"></circle>
|
<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>
|
<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>
|
</svg>
|
||||||
<span id="submit-text">Antrag einreichen</span>
|
<span id="submit-text">Antrag einreichen</span>
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</form>
|
</form>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- Enhanced Status Check Section -->
|
<!-- Enhanced Status Check Section -->
|
||||||
<div class="guest-form-container p-8">
|
<div class="dashboard-card p-8">
|
||||||
<div class="text-center">
|
<div class="text-center">
|
||||||
<div class="inline-flex items-center justify-center w-16 h-16 bg-mercedes-green text-white rounded-xl mb-6">
|
<div class="inline-flex items-center justify-center w-16 h-16 bg-mercedes-green text-white rounded-xl mb-6">
|
||||||
<svg class="w-8 h-8" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
<svg class="w-8 h-8" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
@ -839,7 +676,7 @@
|
|||||||
};
|
};
|
||||||
let isSubmitting = false;
|
let isSubmitting = false;
|
||||||
|
|
||||||
document.addEventListener('DOMContentLoaded', function() {
|
document.addEventListener('DOMContentLoaded', function() {
|
||||||
initializeGuestRequestForm();
|
initializeGuestRequestForm();
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -603,7 +603,7 @@
|
|||||||
<strong>Präzision, Geschwindigkeit und Zuverlässigkeit</strong> nach höchsten Standards.
|
<strong>Präzision, Geschwindigkeit und Zuverlässigkeit</strong> nach höchsten Standards.
|
||||||
</p>
|
</p>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="grid grid-cols-1 md:grid-cols-4 gap-8">
|
<div class="grid grid-cols-1 md:grid-cols-4 gap-8">
|
||||||
<!-- Enhanced Step 1 -->
|
<!-- Enhanced Step 1 -->
|
||||||
<div class="process-step text-center">
|
<div class="process-step text-center">
|
||||||
@ -669,7 +669,7 @@
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- Process Timeline -->
|
<!-- Process Timeline -->
|
||||||
<div class="mt-16 relative">
|
<div class="mt-16 relative">
|
||||||
<div class="absolute top-8 left-0 right-0 h-1 bg-gradient-to-r from-blue-500 via-green-500 via-purple-500 to-orange-500 opacity-30"></div>
|
<div class="absolute top-8 left-0 right-0 h-1 bg-gradient-to-r from-blue-500 via-green-500 via-purple-500 to-orange-500 opacity-30"></div>
|
||||||
|
@ -253,15 +253,15 @@
|
|||||||
<!-- Mercedes-Benz Logo -->
|
<!-- Mercedes-Benz Logo -->
|
||||||
<div class="mercedes-logo inline-flex items-center justify-center w-20 h-20 bg-white/10 backdrop-blur-sm rounded-full mb-6 border border-white/20">
|
<div class="mercedes-logo inline-flex items-center justify-center w-20 h-20 bg-white/10 backdrop-blur-sm rounded-full mb-6 border border-white/20">
|
||||||
<svg class="w-10 h-10 text-mercedes-black dark:text-white" viewBox="0 0 80 80" fill="currentColor">
|
<svg class="w-10 h-10 text-mercedes-black dark:text-white" viewBox="0 0 80 80" fill="currentColor">
|
||||||
<path d="M58.6,4.5C53,1.6,46.7,0,40,0c-6.7,0-13,1.6-18.6,4.5v0C8.7,11.2,0,24.6,0,40c0,15.4,8.7,28.8,21.5,35.5
|
<path d="M58.6,4.5C53,1.6,46.7,0,40,0c-6.7,0-13,1.6-18.6,4.5v0C8.7,11.2,0,24.6,0,40c0,15.4,8.7,28.8,21.5,35.5
|
||||||
C27,78.3,33.3,80,40,80c6.7,0,12.9-1.7,18.5-4.6C71.3,68.8,80,55.4,80,40C80,24.6,71.3,11.2,58.6,4.5z M4,40
|
C27,78.3,33.3,80,40,80c6.7,0,12.9-1.7,18.5-4.6C71.3,68.8,80,55.4,80,40C80,24.6,71.3,11.2,58.6,4.5z M4,40
|
||||||
c0-13.1,7-24.5,17.5-30.9v0C26.6,6,32.5,4.2,39,4l-4.5,32.7L21.5,46.8v0L8.3,57.1C5.6,52,4,46.2,4,40z M58.6,70.8
|
c0-13.1,7-24.5,17.5-30.9v0C26.6,6,32.5,4.2,39,4l-4.5,32.7L21.5,46.8v0L8.3,57.1C5.6,52,4,46.2,4,40z M58.6,70.8
|
||||||
C53.1,74.1,46.8,76,40,76c-6.8,0-13.2-1.9-18.6-5.2c-4.9-2.9-8.9-6.9-11.9-11.7l11.9-4.9v0L40,46.6l18.6,7.5v0l12,4.9
|
C53.1,74.1,46.8,76,40,76c-6.8,0-13.2-1.9-18.6-5.2c-4.9-2.9-8.9-6.9-11.9-11.7l11.9-4.9v0L40,46.6l18.6,7.5v0l12,4.9
|
||||||
C67.6,63.9,63.4,67.9,58.6,70.8z M58.6,46.8L58.6,46.8l-12.9-10L41.1,4c6.3,0.2,12.3,2,17.4,5.1v0C69,15.4,76,26.9,76,40
|
C67.6,63.9,63.4,67.9,58.6,70.8z M58.6,46.8L58.6,46.8l-12.9-10L41.1,4c6.3,0.2,12.3,2,17.4,5.1v0C69,15.4,76,26.9,76,40
|
||||||
c0,6.2-1.5,12-4.3,17.1L58.6,46.8z"/>
|
c0,6.2-1.5,12-4.3,17.1L58.6,46.8z"/>
|
||||||
</svg>
|
</svg>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<h2 class="text-3xl font-bold text-mercedes-black dark:text-white mb-2">
|
<h2 class="text-3xl font-bold text-mercedes-black dark:text-white mb-2">
|
||||||
Bei MYP Platform anmelden
|
Bei MYP Platform anmelden
|
||||||
</h2>
|
</h2>
|
||||||
@ -273,7 +273,7 @@
|
|||||||
<div class="security-indicator">
|
<div class="security-indicator">
|
||||||
<svg class="w-4 h-4 inline mr-2" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
<svg class="w-4 h-4 inline mr-2" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 15v2m-6 4h12a2 2 0 002-2v-6a2 2 0 00-2-2H6a2 2 0 00-2 2v6a2 2 0 002 2zm10-10V7a4 4 0 00-8 0v4h8z"/>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 15v2m-6 4h12a2 2 0 002-2v-6a2 2 0 00-2-2H6a2 2 0 00-2 2v6a2 2 0 002 2zm10-10V7a4 4 0 00-8 0v4h8z"/>
|
||||||
</svg>
|
</svg>
|
||||||
Sichere SSL-Verbindung aktiv
|
Sichere SSL-Verbindung aktiv
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@ -292,7 +292,7 @@
|
|||||||
<div class="absolute inset-y-0 left-0 pl-3 flex items-center pointer-events-none">
|
<div class="absolute inset-y-0 left-0 pl-3 flex items-center pointer-events-none">
|
||||||
<svg class="h-5 w-5 text-mercedes-silver" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
<svg class="h-5 w-5 text-mercedes-silver" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M16 12a4 4 0 10-8 0 4 4 0 008 0zm0 0v1.5a2.5 2.5 0 005 0V12a9 9 0 10-9 9m4.5-1.206a8.959 8.959 0 01-4.5 1.207"/>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M16 12a4 4 0 10-8 0 4 4 0 008 0zm0 0v1.5a2.5 2.5 0 005 0V12a9 9 0 10-9 9m4.5-1.206a8.959 8.959 0 01-4.5 1.207"/>
|
||||||
</svg>
|
</svg>
|
||||||
</div>
|
</div>
|
||||||
{% if form %}
|
{% if form %}
|
||||||
{{ form.email(class="mercedes-input block w-full pl-10 pr-3 py-3 rounded-lg focus:ring-2 focus:ring-mercedes-blue focus:border-mercedes-blue", placeholder="ihre.email@mercedes-benz.com", autocomplete="email") }}
|
{{ form.email(class="mercedes-input block w-full pl-10 pr-3 py-3 rounded-lg focus:ring-2 focus:ring-mercedes-blue focus:border-mercedes-blue", placeholder="ihre.email@mercedes-benz.com", autocomplete="email") }}
|
||||||
@ -301,7 +301,7 @@
|
|||||||
class="mercedes-input block w-full pl-10 pr-3 py-3 rounded-lg focus:ring-2 focus:ring-mercedes-blue focus:border-mercedes-blue"
|
class="mercedes-input block w-full pl-10 pr-3 py-3 rounded-lg focus:ring-2 focus:ring-mercedes-blue focus:border-mercedes-blue"
|
||||||
placeholder="ihre.email@mercedes-benz.com" autocomplete="email">
|
placeholder="ihre.email@mercedes-benz.com" autocomplete="email">
|
||||||
{% endif %}
|
{% endif %}
|
||||||
</div>
|
</div>
|
||||||
{% if form and form.email.errors %}
|
{% if form and form.email.errors %}
|
||||||
<div class="mt-1 text-sm text-mercedes-red">
|
<div class="mt-1 text-sm text-mercedes-red">
|
||||||
{% for error in form.email.errors %}
|
{% for error in form.email.errors %}
|
||||||
@ -309,18 +309,18 @@
|
|||||||
{% endfor %}
|
{% endfor %}
|
||||||
</div>
|
</div>
|
||||||
{% endif %}
|
{% endif %}
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- Password -->
|
<!-- Password -->
|
||||||
<div>
|
<div>
|
||||||
<label for="password" class="block text-sm font-medium text-mercedes-black dark:text-slate-300 mb-2">
|
<label for="password" class="block text-sm font-medium text-mercedes-black dark:text-slate-300 mb-2">
|
||||||
Passwort
|
Passwort
|
||||||
</label>
|
</label>
|
||||||
<div class="relative">
|
<div class="relative">
|
||||||
<div class="absolute inset-y-0 left-0 pl-3 flex items-center pointer-events-none">
|
<div class="absolute inset-y-0 left-0 pl-3 flex items-center pointer-events-none">
|
||||||
<svg class="h-5 w-5 text-mercedes-silver" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
<svg class="h-5 w-5 text-mercedes-silver" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 15v2m-6 4h12a2 2 0 002-2v-6a2 2 0 00-2-2H6a2 2 0 00-2 2v6a2 2 0 002 2zm10-10V7a4 4 0 00-8 0v4h8z"/>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 15v2m-6 4h12a2 2 0 002-2v-6a2 2 0 00-2-2H6a2 2 0 00-2 2v6a2 2 0 002 2zm10-10V7a4 4 0 00-8 0v4h8z"/>
|
||||||
</svg>
|
</svg>
|
||||||
</div>
|
</div>
|
||||||
{% if form %}
|
{% if form %}
|
||||||
{{ form.password(class="mercedes-input block w-full pl-10 pr-10 py-3 rounded-lg focus:ring-2 focus:ring-mercedes-blue focus:border-mercedes-blue", placeholder="Ihr Passwort", autocomplete="current-password") }}
|
{{ form.password(class="mercedes-input block w-full pl-10 pr-10 py-3 rounded-lg focus:ring-2 focus:ring-mercedes-blue focus:border-mercedes-blue", placeholder="Ihr Passwort", autocomplete="current-password") }}
|
||||||
@ -366,8 +366,8 @@
|
|||||||
<input type="checkbox" id="remember_me" name="remember_me"
|
<input type="checkbox" id="remember_me" name="remember_me"
|
||||||
class="w-4 h-4 text-mercedes-blue bg-white dark:bg-slate-800 border-mercedes-silver rounded focus:ring-mercedes-blue focus:ring-2">
|
class="w-4 h-4 text-mercedes-blue bg-white dark:bg-slate-800 border-mercedes-silver rounded focus:ring-mercedes-blue focus:ring-2">
|
||||||
<label for="remember_me" class="ml-2 text-sm text-mercedes-black dark:text-slate-300">
|
<label for="remember_me" class="ml-2 text-sm text-mercedes-black dark:text-slate-300">
|
||||||
Angemeldet bleiben
|
Angemeldet bleiben
|
||||||
</label>
|
</label>
|
||||||
{% endif %}
|
{% endif %}
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
@ -381,11 +381,11 @@
|
|||||||
|
|
||||||
<!-- Rate Limiting Warning -->
|
<!-- Rate Limiting Warning -->
|
||||||
<div id="rate-limit-warning" class="hidden bg-yellow-50 dark:bg-yellow-900/20 border border-yellow-200 dark:border-yellow-800 rounded-lg p-3">
|
<div id="rate-limit-warning" class="hidden bg-yellow-50 dark:bg-yellow-900/20 border border-yellow-200 dark:border-yellow-800 rounded-lg p-3">
|
||||||
<div class="flex">
|
<div class="flex">
|
||||||
<svg class="h-5 w-5 text-yellow-400" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
<svg class="h-5 w-5 text-yellow-400" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 9v2m0 4h.01m-6.938 4h13.856c1.54 0 2.502-1.667 1.732-2.5L13.732 4c-.77-.833-1.964-.833-2.732 0L4.082 16.5c-.77.833.192 2.5 1.732 2.5z"/>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 9v2m0 4h.01m-6.938 4h13.856c1.54 0 2.502-1.667 1.732-2.5L13.732 4c-.77-.833-1.964-.833-2.732 0L4.082 16.5c-.77.833.192 2.5 1.732 2.5z"/>
|
||||||
</svg>
|
</svg>
|
||||||
<div class="ml-3">
|
<div class="ml-3">
|
||||||
<p class="text-sm text-yellow-800 dark:text-yellow-200">
|
<p class="text-sm text-yellow-800 dark:text-yellow-200">
|
||||||
<strong>Sicherheitshinweis:</strong> Bei mehreren fehlgeschlagenen Anmeldeversuchen wird Ihr Konto vorübergehend gesperrt.
|
<strong>Sicherheitshinweis:</strong> Bei mehreren fehlgeschlagenen Anmeldeversuchen wird Ihr Konto vorübergehend gesperrt.
|
||||||
</p>
|
</p>
|
||||||
@ -405,7 +405,7 @@
|
|||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
</form>
|
</form>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- Alternative Actions -->
|
<!-- Alternative Actions -->
|
||||||
<div class="text-center space-y-4">
|
<div class="text-center space-y-4">
|
||||||
@ -436,7 +436,7 @@
|
|||||||
</svg>
|
</svg>
|
||||||
Zurück zur Startseite
|
Zurück zur Startseite
|
||||||
</a>
|
</a>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@ -450,7 +450,7 @@
|
|||||||
const MAX_ATTEMPTS = 5;
|
const MAX_ATTEMPTS = 5;
|
||||||
const LOCKOUT_DURATION = 15 * 60 * 1000; // 15 minutes
|
const LOCKOUT_DURATION = 15 * 60 * 1000; // 15 minutes
|
||||||
|
|
||||||
document.addEventListener('DOMContentLoaded', function() {
|
document.addEventListener('DOMContentLoaded', function() {
|
||||||
initializeLoginForm();
|
initializeLoginForm();
|
||||||
checkRateLimit();
|
checkRateLimit();
|
||||||
setupFormValidation();
|
setupFormValidation();
|
||||||
@ -588,7 +588,7 @@
|
|||||||
document.addEventListener('keypress', function(e) {
|
document.addEventListener('keypress', function(e) {
|
||||||
// Enter key submits form
|
// Enter key submits form
|
||||||
if (e.key === 'Enter' && e.target.form === document.getElementById('loginForm')) {
|
if (e.key === 'Enter' && e.target.form === document.getElementById('loginForm')) {
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
document.getElementById('loginForm').dispatchEvent(new Event('submit'));
|
document.getElementById('loginForm').dispatchEvent(new Event('submit'));
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
@ -899,8 +899,8 @@
|
|||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 8v4m0 4h.01M21 12a9 9 0 11-18 0 9 9 0 0118 0z"/>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 8v4m0 4h.01M21 12a9 9 0 11-18 0 9 9 0 0118 0z"/>
|
||||||
</svg>
|
</svg>
|
||||||
${message}
|
${message}
|
||||||
</div>
|
</div>
|
||||||
`;
|
`;
|
||||||
|
|
||||||
input.parentNode.appendChild(errorDiv);
|
input.parentNode.appendChild(errorDiv);
|
||||||
|
|
||||||
@ -917,8 +917,8 @@
|
|||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 9v2m0 4h.01m-6.938 4h13.856c1.54 0 2.502-1.667 1.732-2.5L13.732 4c-.77-.833-1.964-.833-2.732 0L4.082 16.5c-.77.833.192 2.5 1.732 2.5z"/>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 9v2m0 4h.01m-6.938 4h13.856c1.54 0 2.502-1.667 1.732-2.5L13.732 4c-.77-.833-1.964-.833-2.732 0L4.082 16.5c-.77.833.192 2.5 1.732 2.5z"/>
|
||||||
</svg>
|
</svg>
|
||||||
${message}
|
${message}
|
||||||
</div>
|
</div>
|
||||||
`;
|
`;
|
||||||
input.parentNode.appendChild(warningDiv);
|
input.parentNode.appendChild(warningDiv);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -941,7 +941,7 @@
|
|||||||
form.reset();
|
form.reset();
|
||||||
|
|
||||||
const inputs = form.querySelectorAll('input');
|
const inputs = form.querySelectorAll('input');
|
||||||
inputs.forEach(input => {
|
inputs.forEach(input => {
|
||||||
clearError(input);
|
clearError(input);
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -981,9 +981,9 @@
|
|||||||
document.body.appendChild(toast);
|
document.body.appendChild(toast);
|
||||||
|
|
||||||
// Animate in
|
// Animate in
|
||||||
setTimeout(() => {
|
setTimeout(() => {
|
||||||
toast.classList.remove('translate-x-full', 'opacity-0');
|
toast.classList.remove('translate-x-full', 'opacity-0');
|
||||||
}, 100);
|
}, 100);
|
||||||
|
|
||||||
// Auto-remove after 5 seconds
|
// Auto-remove after 5 seconds
|
||||||
setTimeout(() => {
|
setTimeout(() => {
|
||||||
|
@ -451,8 +451,8 @@
|
|||||||
<div class="w-16 h-16 flex-shrink-0 bg-mercedes-blue text-white rounded-xl flex items-center justify-center">
|
<div class="w-16 h-16 flex-shrink-0 bg-mercedes-blue text-white rounded-xl flex items-center justify-center">
|
||||||
<svg class="w-8 h-8" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
<svg class="w-8 h-8" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M5 12h14M5 12a2 2 0 01-2-2V6a2 2 0 012-2h14a2 2 0 012 2v4a2 2 0 01-2 2M5 12a2 2 0 00-2 2v4a2 2 0 002 2h14a2 2 0 002-2v-4a2 2 0 00-2-2m-2-4h.01M17 16h.01"/>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M5 12h14M5 12a2 2 0 01-2-2V6a2 2 0 012-2h14a2 2 0 012 2v4a2 2 0 01-2 2M5 12a2 2 0 00-2 2v4a2 2 0 002 2h14a2 2 0 002-2v-4a2 2 0 00-2-2m-2-4h.01M17 16h.01"/>
|
||||||
</svg>
|
</svg>
|
||||||
</div>
|
</div>
|
||||||
<div>
|
<div>
|
||||||
<h1 class="text-4xl font-bold text-mercedes-black dark:text-white tracking-tight">3D-Drucker</h1>
|
<h1 class="text-4xl font-bold text-mercedes-black dark:text-white tracking-tight">3D-Drucker</h1>
|
||||||
<p class="text-mercedes-gray dark:text-slate-400 mt-1 text-lg">Live-Überwachung und Verwaltung Ihrer Produktionseinheiten</p>
|
<p class="text-mercedes-gray dark:text-slate-400 mt-1 text-lg">Live-Überwachung und Verwaltung Ihrer Produktionseinheiten</p>
|
||||||
@ -501,12 +501,12 @@
|
|||||||
<div class="flex items-center text-xs text-green-600 dark:text-green-400">
|
<div class="flex items-center text-xs text-green-600 dark:text-green-400">
|
||||||
<div class="w-2 h-2 bg-green-500 rounded-full mr-2 status-pulse"></div>
|
<div class="w-2 h-2 bg-green-500 rounded-full mr-2 status-pulse"></div>
|
||||||
<span>Betriebsbereit</span>
|
<span>Betriebsbereit</span>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="w-12 h-12 bg-green-100 dark:bg-green-900/30 rounded-xl flex items-center justify-center">
|
<div class="w-12 h-12 bg-green-100 dark:bg-green-900/30 rounded-xl flex items-center justify-center">
|
||||||
<div class="w-6 h-6 bg-green-500 rounded-full"></div>
|
<div class="w-6 h-6 bg-green-500 rounded-full"></div>
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
<div class="mt-4 pt-4 border-t border-green-200 dark:border-green-800">
|
<div class="mt-4 pt-4 border-t border-green-200 dark:border-green-800">
|
||||||
<div class="text-xs text-mercedes-gray dark:text-slate-400">
|
<div class="text-xs text-mercedes-gray dark:text-slate-400">
|
||||||
<span class="font-medium" id="online-percentage">0%</span> aller Drucker
|
<span class="font-medium" id="online-percentage">0%</span> aller Drucker
|
||||||
@ -522,12 +522,12 @@
|
|||||||
<div class="flex items-center text-xs text-red-600 dark:text-red-400">
|
<div class="flex items-center text-xs text-red-600 dark:text-red-400">
|
||||||
<div class="w-2 h-2 bg-red-500 rounded-full mr-2"></div>
|
<div class="w-2 h-2 bg-red-500 rounded-full mr-2"></div>
|
||||||
<span>Nicht verfügbar</span>
|
<span>Nicht verfügbar</span>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="w-12 h-12 bg-red-100 dark:bg-red-900/30 rounded-xl flex items-center justify-center">
|
<div class="w-12 h-12 bg-red-100 dark:bg-red-900/30 rounded-xl flex items-center justify-center">
|
||||||
<div class="w-6 h-6 bg-red-500 rounded-full"></div>
|
<div class="w-6 h-6 bg-red-500 rounded-full"></div>
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
<div class="mt-4 pt-4 border-t border-red-200 dark:border-red-800">
|
<div class="mt-4 pt-4 border-t border-red-200 dark:border-red-800">
|
||||||
<div class="text-xs text-mercedes-gray dark:text-slate-400">
|
<div class="text-xs text-mercedes-gray dark:text-slate-400">
|
||||||
<span class="font-medium" id="offline-percentage">0%</span> aller Drucker
|
<span class="font-medium" id="offline-percentage">0%</span> aller Drucker
|
||||||
@ -543,12 +543,12 @@
|
|||||||
<div class="flex items-center text-xs text-blue-600 dark:text-blue-400">
|
<div class="flex items-center text-xs text-blue-600 dark:text-blue-400">
|
||||||
<div class="w-2 h-2 bg-blue-500 rounded-full mr-2 status-pulse"></div>
|
<div class="w-2 h-2 bg-blue-500 rounded-full mr-2 status-pulse"></div>
|
||||||
<span>Druckt gerade</span>
|
<span>Druckt gerade</span>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="w-12 h-12 bg-blue-100 dark:bg-blue-900/30 rounded-xl flex items-center justify-center">
|
<div class="w-12 h-12 bg-blue-100 dark:bg-blue-900/30 rounded-xl flex items-center justify-center">
|
||||||
<div class="w-6 h-6 bg-blue-500 rounded-full animate-pulse"></div>
|
<div class="w-6 h-6 bg-blue-500 rounded-full animate-pulse"></div>
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
<div class="mt-4 pt-4 border-t border-blue-200 dark:border-blue-800">
|
<div class="mt-4 pt-4 border-t border-blue-200 dark:border-blue-800">
|
||||||
<div class="text-xs text-mercedes-gray dark:text-slate-400">
|
<div class="text-xs text-mercedes-gray dark:text-slate-400">
|
||||||
<span class="font-medium" id="active-percentage">0%</span> Auslastung
|
<span class="font-medium" id="active-percentage">0%</span> Auslastung
|
||||||
@ -566,7 +566,7 @@
|
|||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M5 12h14M5 12a2 2 0 01-2-2V6a2 2 0 012-2h14a2 2 0 012 2v4a2 2 0 01-2 2M5 12a2 2 0 00-2 2v4a2 2 0 002 2h14a2 2 0 002-2v-4a2 2 0 00-2-2m-2-4h.01M17 16h.01"/>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M5 12h14M5 12a2 2 0 01-2-2V6a2 2 0 012-2h14a2 2 0 012 2v4a2 2 0 01-2 2M5 12a2 2 0 00-2 2v4a2 2 0 002 2h14a2 2 0 002-2v-4a2 2 0 00-2-2m-2-4h.01M17 16h.01"/>
|
||||||
</svg>
|
</svg>
|
||||||
<span>Drucker registriert</span>
|
<span>Drucker registriert</span>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="w-12 h-12 bg-mercedes-silver rounded-xl flex items-center justify-center">
|
<div class="w-12 h-12 bg-mercedes-silver rounded-xl flex items-center justify-center">
|
||||||
<svg class="w-6 h-6 text-mercedes-black dark:text-white" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
<svg class="w-6 h-6 text-mercedes-black dark:text-white" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
@ -688,7 +688,7 @@
|
|||||||
<option value="">Alle Standorte</option>
|
<option value="">Alle Standorte</option>
|
||||||
<!-- Wird dynamisch gefüllt -->
|
<!-- Wird dynamisch gefüllt -->
|
||||||
</select>
|
</select>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- Model Filter -->
|
<!-- Model Filter -->
|
||||||
<div>
|
<div>
|
||||||
@ -702,9 +702,9 @@
|
|||||||
<option value="">Alle Modelle</option>
|
<option value="">Alle Modelle</option>
|
||||||
<!-- Wird dynamisch gefüllt -->
|
<!-- Wird dynamisch gefüllt -->
|
||||||
</select>
|
</select>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- Advanced Filter Options -->
|
<!-- Advanced Filter Options -->
|
||||||
<div class="mt-6 flex flex-wrap items-center justify-between gap-4">
|
<div class="mt-6 flex flex-wrap items-center justify-between gap-4">
|
||||||
<div class="flex flex-wrap gap-4">
|
<div class="flex flex-wrap gap-4">
|
||||||
@ -770,8 +770,8 @@
|
|||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- Loading State -->
|
<!-- Loading State -->
|
||||||
<div id="loading-state" class="space-y-6">
|
<div id="loading-state" class="space-y-6">
|
||||||
<div class="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-6">
|
<div class="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-6">
|
||||||
<div class="printer-card p-6">
|
<div class="printer-card p-6">
|
||||||
@ -835,9 +835,9 @@
|
|||||||
<div class="text-center">
|
<div class="text-center">
|
||||||
<div class="text-mercedes-gray dark:text-slate-400 mb-4">
|
<div class="text-mercedes-gray dark:text-slate-400 mb-4">
|
||||||
<svg class="w-8 h-8 mx-auto mb-3 animate-spin text-mercedes-blue" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
<svg class="w-8 h-8 mx-auto mb-3 animate-spin text-mercedes-blue" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M4 4v5h.582m15.356 2A8.001 8.001 0 004.582 9m0 0H9m11 11v-5h-.581m0 0a8.003 8.003 0 01-15.357-2m15.357 2H15"/>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M4 4v5h.582m15.356 2A8.001 8.001 0 004.582 9m0 0H9m11 11v-5h-.581m0 0a8.003 8.003 0 01-15.357-2m15.357 2H15"/>
|
||||||
</svg>
|
</svg>
|
||||||
</div>
|
</div>
|
||||||
<p class="text-mercedes-gray dark:text-slate-400">Lade Drucker-Informationen...</p>
|
<p class="text-mercedes-gray dark:text-slate-400">Lade Drucker-Informationen...</p>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@ -846,16 +846,16 @@
|
|||||||
<div id="printers-container" class="hidden">
|
<div id="printers-container" class="hidden">
|
||||||
<div id="printers-grid" class="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-6">
|
<div id="printers-grid" class="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-6">
|
||||||
<!-- Printers will be loaded here -->
|
<!-- Printers will be loaded here -->
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- Empty State -->
|
<!-- Empty State -->
|
||||||
<div id="empty-state" class="hidden col-span-full py-16 text-center">
|
<div id="empty-state" class="hidden col-span-full py-16 text-center">
|
||||||
<div class="max-w-md mx-auto">
|
<div class="max-w-md mx-auto">
|
||||||
<div class="text-mercedes-silver mb-6">
|
<div class="text-mercedes-silver mb-6">
|
||||||
<svg class="w-20 h-20 mx-auto" fill="none" viewBox="0 0 24 24" stroke="currentColor">
|
<svg class="w-20 h-20 mx-auto" fill="none" viewBox="0 0 24 24" stroke="currentColor">
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="1" d="M5 12h14M5 12a2 2 0 01-2-2V6a2 2 0 012-2h14a2 2 0 012 2v4a2 2 0 01-2 2M5 12a2 2 0 00-2 2v4a2 2 0 002 2h14a2 2 0 002-2v-4a2 2 0 00-2-2m-2-4h.01M17 16h.01"/>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="1" d="M5 12h14M5 12a2 2 0 01-2-2V6a2 2 0 012-2h14a2 2 0 012 2v4a2 2 0 01-2 2M5 12a2 2 0 00-2 2v4a2 2 0 002 2h14a2 2 0 002-2v-4a2 2 0 00-2-2m-2-4h.01M17 16h.01"/>
|
||||||
</svg>
|
</svg>
|
||||||
</div>
|
</div>
|
||||||
<h3 class="text-2xl font-semibold text-mercedes-black dark:text-white mb-3">Keine Drucker gefunden</h3>
|
<h3 class="text-2xl font-semibold text-mercedes-black dark:text-white mb-3">Keine Drucker gefunden</h3>
|
||||||
<p class="text-mercedes-gray dark:text-slate-400 mb-8 leading-relaxed">
|
<p class="text-mercedes-gray dark:text-slate-400 mb-8 leading-relaxed">
|
||||||
Es wurden keine 3D-Drucker gefunden, die den aktuellen Filterkriterien entsprechen.
|
Es wurden keine 3D-Drucker gefunden, die den aktuellen Filterkriterien entsprechen.
|
||||||
@ -865,11 +865,11 @@
|
|||||||
<button onclick="clearAllFilters()" class="btn-secondary">
|
<button onclick="clearAllFilters()" class="btn-secondary">
|
||||||
Filter zurücksetzen
|
Filter zurücksetzen
|
||||||
</button>
|
</button>
|
||||||
<button onclick="openAddPrinterModal()" class="btn-primary">
|
<button onclick="openAddPrinterModal()" class="btn-primary">
|
||||||
Ersten Drucker hinzufügen
|
Ersten Drucker hinzufügen
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- No Results State -->
|
<!-- No Results State -->
|
||||||
@ -898,7 +898,7 @@
|
|||||||
<div class="flex items-center justify-center min-h-screen p-4">
|
<div class="flex items-center justify-center min-h-screen p-4">
|
||||||
<div class="mercedes-modal max-w-2xl w-full p-8 transform transition-all duration-300 scale-95 opacity-0" id="printerModalContent">
|
<div class="mercedes-modal max-w-2xl w-full p-8 transform transition-all duration-300 scale-95 opacity-0" id="printerModalContent">
|
||||||
<div class="flex justify-between items-center mb-6">
|
<div class="flex justify-between items-center mb-6">
|
||||||
<div>
|
<div>
|
||||||
<h3 id="printerModalTitle" class="text-2xl font-bold text-mercedes-black dark:text-white mb-2">
|
<h3 id="printerModalTitle" class="text-2xl font-bold text-mercedes-black dark:text-white mb-2">
|
||||||
Drucker hinzufügen
|
Drucker hinzufügen
|
||||||
</h3>
|
</h3>
|
||||||
@ -913,7 +913,7 @@
|
|||||||
|
|
||||||
<form id="printerForm" class="space-y-6">
|
<form id="printerForm" class="space-y-6">
|
||||||
<input type="hidden" id="printerId" name="printerId">
|
<input type="hidden" id="printerId" name="printerId">
|
||||||
|
|
||||||
<!-- Basic Information -->
|
<!-- Basic Information -->
|
||||||
<div class="space-y-4">
|
<div class="space-y-4">
|
||||||
<h4 class="text-lg font-semibold text-mercedes-black dark:text-white border-b border-mercedes-silver pb-2">
|
<h4 class="text-lg font-semibold text-mercedes-black dark:text-white border-b border-mercedes-silver pb-2">
|
||||||
@ -921,20 +921,20 @@
|
|||||||
</h4>
|
</h4>
|
||||||
|
|
||||||
<div class="grid grid-cols-1 md:grid-cols-2 gap-4">
|
<div class="grid grid-cols-1 md:grid-cols-2 gap-4">
|
||||||
<div>
|
<div>
|
||||||
<label for="printerName" class="block text-sm font-medium text-mercedes-black dark:text-slate-300 mb-2">
|
<label for="printerName" class="block text-sm font-medium text-mercedes-black dark:text-slate-300 mb-2">
|
||||||
Drucker-Name <span class="text-red-500">*</span>
|
Drucker-Name <span class="text-red-500">*</span>
|
||||||
</label>
|
</label>
|
||||||
<input type="text" id="printerName" name="name" required
|
<input type="text" id="printerName" name="name" required
|
||||||
class="mercedes-form-input block w-full px-4 py-3 rounded-lg"
|
class="mercedes-form-input block w-full px-4 py-3 rounded-lg"
|
||||||
placeholder="z.B. Ultimaker S3 #01">
|
placeholder="z.B. Ultimaker S3 #01">
|
||||||
<p class="text-xs text-mercedes-gray dark:text-slate-400 mt-1">Eindeutiger Name zur Identifikation</p>
|
<p class="text-xs text-mercedes-gray dark:text-slate-400 mt-1">Eindeutiger Name zur Identifikation</p>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div>
|
<div>
|
||||||
<label for="printerModel" class="block text-sm font-medium text-mercedes-black dark:text-slate-300 mb-2">
|
<label for="printerModel" class="block text-sm font-medium text-mercedes-black dark:text-slate-300 mb-2">
|
||||||
Modell
|
Modell
|
||||||
</label>
|
</label>
|
||||||
<select id="printerModel" name="model" class="mercedes-form-input block w-full px-4 py-3 rounded-lg">
|
<select id="printerModel" name="model" class="mercedes-form-input block w-full px-4 py-3 rounded-lg">
|
||||||
<option value="">Modell auswählen...</option>
|
<option value="">Modell auswählen...</option>
|
||||||
<option value="Ultimaker S3">Ultimaker S3</option>
|
<option value="Ultimaker S3">Ultimaker S3</option>
|
||||||
@ -953,30 +953,30 @@
|
|||||||
<input type="text" id="customModel" name="customModel"
|
<input type="text" id="customModel" name="customModel"
|
||||||
class="mercedes-form-input block w-full px-4 py-3 rounded-lg"
|
class="mercedes-form-input block w-full px-4 py-3 rounded-lg"
|
||||||
placeholder="Geben Sie das Druckermodell ein">
|
placeholder="Geben Sie das Druckermodell ein">
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div>
|
<div>
|
||||||
<label for="printerLocation" class="block text-sm font-medium text-mercedes-black dark:text-slate-300 mb-2">
|
<label for="printerLocation" class="block text-sm font-medium text-mercedes-black dark:text-slate-300 mb-2">
|
||||||
Standort <span class="text-red-500">*</span>
|
Standort <span class="text-red-500">*</span>
|
||||||
</label>
|
</label>
|
||||||
<input type="text" id="printerLocation" name="location" required
|
<input type="text" id="printerLocation" name="location" required
|
||||||
class="mercedes-form-input block w-full px-4 py-3 rounded-lg"
|
class="mercedes-form-input block w-full px-4 py-3 rounded-lg"
|
||||||
placeholder="z.B. Produktionshalle A, Raum 101">
|
placeholder="z.B. Produktionshalle A, Raum 101">
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div>
|
<div>
|
||||||
<label for="printerIP" class="block text-sm font-medium text-mercedes-black dark:text-slate-300 mb-2">
|
<label for="printerIP" class="block text-sm font-medium text-mercedes-black dark:text-slate-300 mb-2">
|
||||||
IP-Adresse
|
IP-Adresse
|
||||||
</label>
|
</label>
|
||||||
<input type="text" id="printerIP" name="ip_address"
|
<input type="text" id="printerIP" name="ip_address"
|
||||||
class="mercedes-form-input block w-full px-4 py-3 rounded-lg"
|
class="mercedes-form-input block w-full px-4 py-3 rounded-lg"
|
||||||
placeholder="192.168.1.100"
|
placeholder="192.168.1.100"
|
||||||
pattern="^((25[0-5]|(2[0-4]|1\d|[1-9]|)\d)\.?\b){4}$">
|
pattern="^((25[0-5]|(2[0-4]|1\d|[1-9]|)\d)\.?\b){4}$">
|
||||||
<p class="text-xs text-mercedes-gray dark:text-slate-400 mt-1">Für Netzwerk-Überwachung</p>
|
<p class="text-xs text-mercedes-gray dark:text-slate-400 mt-1">Für Netzwerk-Überwachung</p>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- Technical Specifications -->
|
<!-- Technical Specifications -->
|
||||||
<div class="space-y-4">
|
<div class="space-y-4">
|
||||||
<h4 class="text-lg font-semibold text-mercedes-black dark:text-white border-b border-mercedes-silver pb-2">
|
<h4 class="text-lg font-semibold text-mercedes-black dark:text-white border-b border-mercedes-silver pb-2">
|
||||||
@ -1056,14 +1056,14 @@
|
|||||||
|
|
||||||
<div class="grid grid-cols-1 md:grid-cols-2 gap-6">
|
<div class="grid grid-cols-1 md:grid-cols-2 gap-6">
|
||||||
<div class="space-y-4">
|
<div class="space-y-4">
|
||||||
<div class="flex items-center">
|
<div class="flex items-center">
|
||||||
<input type="checkbox" id="printerActive" name="active" checked
|
<input type="checkbox" id="printerActive" name="active" checked
|
||||||
class="w-4 h-4 text-mercedes-blue bg-white dark:bg-slate-800 border-mercedes-silver rounded focus:ring-mercedes-blue focus:ring-2">
|
class="w-4 h-4 text-mercedes-blue bg-white dark:bg-slate-800 border-mercedes-silver rounded focus:ring-mercedes-blue focus:ring-2">
|
||||||
<label for="printerActive" class="ml-3 text-sm text-mercedes-black dark:text-slate-300">
|
<label for="printerActive" class="ml-3 text-sm text-mercedes-black dark:text-slate-300">
|
||||||
Drucker aktiv
|
Drucker aktiv
|
||||||
</label>
|
</label>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="flex items-center">
|
<div class="flex items-center">
|
||||||
<input type="checkbox" id="autoQueue" name="auto_queue"
|
<input type="checkbox" id="autoQueue" name="auto_queue"
|
||||||
class="w-4 h-4 text-mercedes-blue bg-white dark:bg-slate-800 border-mercedes-silver rounded focus:ring-mercedes-blue focus:ring-2">
|
class="w-4 h-4 text-mercedes-blue bg-white dark:bg-slate-800 border-mercedes-silver rounded focus:ring-mercedes-blue focus:ring-2">
|
||||||
@ -1123,22 +1123,22 @@
|
|||||||
</button>
|
</button>
|
||||||
|
|
||||||
<div class="flex items-center gap-3">
|
<div class="flex items-center gap-3">
|
||||||
<button type="button" onclick="closePrinterModal()" class="btn-secondary">
|
<button type="button" onclick="closePrinterModal()" class="btn-secondary">
|
||||||
Abbrechen
|
Abbrechen
|
||||||
</button>
|
</button>
|
||||||
<button type="submit" class="btn-primary flex items-center gap-2">
|
<button type="submit" class="btn-primary flex items-center gap-2">
|
||||||
<svg class="w-4 h-4" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
<svg class="w-4 h-4" 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 stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M5 13l4 4L19 7"/>
|
||||||
</svg>
|
</svg>
|
||||||
Speichern
|
Speichern
|
||||||
</button>
|
</button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</form>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</form>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<!-- Enhanced Printer Details Modal -->
|
<!-- Enhanced Printer Details Modal -->
|
||||||
<div id="printerDetailsModal" class="fixed inset-0 bg-black/60 backdrop-blur-sm hidden z-50">
|
<div id="printerDetailsModal" class="fixed inset-0 bg-black/60 backdrop-blur-sm hidden z-50">
|
||||||
<div class="flex items-center justify-center min-h-screen p-4">
|
<div class="flex items-center justify-center min-h-screen p-4">
|
||||||
@ -1149,14 +1149,14 @@
|
|||||||
Drucker Details
|
Drucker Details
|
||||||
</h3>
|
</h3>
|
||||||
<p class="text-mercedes-gray dark:text-slate-400">Live-Informationen und Steuerungsoptionen</p>
|
<p class="text-mercedes-gray dark:text-slate-400">Live-Informationen und Steuerungsoptionen</p>
|
||||||
</div>
|
</div>
|
||||||
<button onclick="closePrinterDetailsModal()" class="p-2 hover:bg-gray-100 dark:hover:bg-slate-700 rounded-lg transition-colors">
|
<button onclick="closePrinterDetailsModal()" class="p-2 hover:bg-gray-100 dark:hover:bg-slate-700 rounded-lg transition-colors">
|
||||||
<svg class="w-6 h-6 text-mercedes-gray dark:text-slate-400" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
<svg class="w-6 h-6 text-mercedes-gray dark:text-slate-400" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M6 18L18 6M6 6l12 12"/>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M6 18L18 6M6 6l12 12"/>
|
||||||
</svg>
|
</svg>
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div id="printerDetailsContent" class="space-y-6">
|
<div id="printerDetailsContent" class="space-y-6">
|
||||||
<!-- Content will be loaded dynamically -->
|
<!-- Content will be loaded dynamically -->
|
||||||
<div class="grid grid-cols-1 lg:grid-cols-3 gap-6">
|
<div class="grid grid-cols-1 lg:grid-cols-3 gap-6">
|
||||||
@ -1213,10 +1213,10 @@
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script>
|
<script>
|
||||||
let allPrinters = [];
|
let allPrinters = [];
|
||||||
@ -1273,22 +1273,22 @@ class PrinterManager {
|
|||||||
try {
|
try {
|
||||||
this.showLoadingState();
|
this.showLoadingState();
|
||||||
|
|
||||||
const response = await fetch('/api/printers');
|
const response = await fetch('/api/printers');
|
||||||
const data = await response.json();
|
const data = await response.json();
|
||||||
|
|
||||||
if (data.success) {
|
if (data.success) {
|
||||||
allPrinters = data.printers || [];
|
allPrinters = data.printers || [];
|
||||||
this.applyFilters();
|
this.applyFilters();
|
||||||
this.updateStatistics();
|
this.updateStatistics();
|
||||||
this.populateFilterDropdowns();
|
this.populateFilterDropdowns();
|
||||||
this.updateLastUpdateTime();
|
this.updateLastUpdateTime();
|
||||||
} else {
|
} else {
|
||||||
this.showError('Fehler beim Laden der Drucker: ' + data.message);
|
this.showError('Fehler beim Laden der Drucker: ' + data.message);
|
||||||
}
|
}
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
console.error('Error loading printers:', error);
|
console.error('Error loading printers:', error);
|
||||||
this.showError('Fehler beim Laden der Drucker');
|
this.showError('Fehler beim Laden der Drucker');
|
||||||
} finally {
|
} finally {
|
||||||
this.hideLoadingState();
|
this.hideLoadingState();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1366,20 +1366,20 @@ class PrinterManager {
|
|||||||
}
|
}
|
||||||
|
|
||||||
displayPrinters() {
|
displayPrinters() {
|
||||||
const grid = document.getElementById('printers-grid');
|
const grid = document.getElementById('printers-grid');
|
||||||
const emptyState = document.getElementById('empty-state');
|
const emptyState = document.getElementById('empty-state');
|
||||||
const noResultsState = document.getElementById('no-results-state');
|
const noResultsState = document.getElementById('no-results-state');
|
||||||
|
|
||||||
if (allPrinters.length === 0) {
|
if (allPrinters.length === 0) {
|
||||||
grid.innerHTML = '';
|
grid.innerHTML = '';
|
||||||
emptyState.classList.remove('hidden');
|
emptyState.classList.remove('hidden');
|
||||||
noResultsState.classList.add('hidden');
|
noResultsState.classList.add('hidden');
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (filteredPrinters.length === 0) {
|
if (filteredPrinters.length === 0) {
|
||||||
grid.innerHTML = '';
|
grid.innerHTML = '';
|
||||||
emptyState.classList.add('hidden');
|
emptyState.classList.add('hidden');
|
||||||
noResultsState.classList.remove('hidden');
|
noResultsState.classList.remove('hidden');
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@ -1400,24 +1400,24 @@ class PrinterManager {
|
|||||||
const statusClasses = this.getStatusClasses(printer.status);
|
const statusClasses = this.getStatusClasses(printer.status);
|
||||||
const temperature = printer.temperature || {};
|
const temperature = printer.temperature || {};
|
||||||
const currentJob = printer.current_job || {};
|
const currentJob = printer.current_job || {};
|
||||||
|
|
||||||
return `
|
return `
|
||||||
<div class="printer-card ${statusClasses.container} p-6" data-printer-id="${printer.id}">
|
<div class="printer-card ${statusClasses.container} p-6" data-printer-id="${printer.id}">
|
||||||
<div class="flex items-center justify-between mb-4">
|
<div class="flex items-center justify-between mb-4">
|
||||||
<div class="flex items-center gap-3">
|
<div class="flex items-center gap-3">
|
||||||
<div class="w-12 h-12 ${statusClasses.iconBg} rounded-xl flex items-center justify-center">
|
<div class="w-12 h-12 ${statusClasses.iconBg} rounded-xl flex items-center justify-center">
|
||||||
${this.getStatusIcon(printer.status)}
|
${this.getStatusIcon(printer.status)}
|
||||||
</div>
|
</div>
|
||||||
<div>
|
<div>
|
||||||
<h3 class="text-lg font-semibold text-mercedes-black dark:text-white">${printer.name}</h3>
|
<h3 class="text-lg font-semibold text-mercedes-black dark:text-white">${printer.name}</h3>
|
||||||
<p class="text-sm text-mercedes-gray dark:text-slate-400">${printer.model || 'Unbekanntes Modell'}</p>
|
<p class="text-sm text-mercedes-gray dark:text-slate-400">${printer.model || 'Unbekanntes Modell'}</p>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<span class="inline-flex items-center px-3 py-1 rounded-full text-xs font-medium ${statusClasses.badge}">
|
<span class="inline-flex items-center px-3 py-1 rounded-full text-xs font-medium ${statusClasses.badge}">
|
||||||
${this.getStatusText(printer.status)}
|
${this.getStatusText(printer.status)}
|
||||||
</span>
|
</span>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
${printer.status === 'printing' && currentJob.progress ? `
|
${printer.status === 'printing' && currentJob.progress ? `
|
||||||
<div class="mb-4">
|
<div class="mb-4">
|
||||||
<div class="flex justify-between text-sm text-mercedes-gray dark:text-slate-400 mb-2">
|
<div class="flex justify-between text-sm text-mercedes-gray dark:text-slate-400 mb-2">
|
||||||
@ -1430,7 +1430,7 @@ class PrinterManager {
|
|||||||
${currentJob.time_remaining ? `
|
${currentJob.time_remaining ? `
|
||||||
<div class="text-xs text-mercedes-gray dark:text-slate-400 mt-1">
|
<div class="text-xs text-mercedes-gray dark:text-slate-400 mt-1">
|
||||||
Verbleibend: ${this.formatDuration(currentJob.time_remaining)}
|
Verbleibend: ${this.formatDuration(currentJob.time_remaining)}
|
||||||
</div>
|
</div>
|
||||||
` : ''}
|
` : ''}
|
||||||
</div>
|
</div>
|
||||||
` : ''}
|
` : ''}
|
||||||
@ -1463,30 +1463,30 @@ class PrinterManager {
|
|||||||
<p class="text-mercedes-black dark:text-white">${this.formatUptime(printer.uptime)}</p>
|
<p class="text-mercedes-black dark:text-white">${this.formatUptime(printer.uptime)}</p>
|
||||||
</div>
|
</div>
|
||||||
`}
|
`}
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="flex gap-2">
|
<div class="flex gap-2">
|
||||||
<button onclick="printerManager.openPrinterDetails('${printer.id}')"
|
<button onclick="printerManager.openPrinterDetails('${printer.id}')"
|
||||||
class="printer-action-btn btn-details flex-1">
|
class="printer-action-btn btn-details flex-1">
|
||||||
<svg class="w-4 h-4" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
<svg class="w-4 h-4" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M15 12a3 3 0 11-6 0 3 3 0 016 0z"/>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M15 12a3 3 0 11-6 0 3 3 0 016 0z"/>
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M2.458 12C3.732 7.943 7.523 5 12 5c4.478 0 8.268 2.943 9.542 7-1.274 4.057-5.064 7-9.542 7-4.477 0-8.268-2.943-9.542-7z"/>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M2.458 12C3.732 7.943 7.523 5 12 5c4.478 0 8.268 2.943 9.542 7-1.274 4.057-5.064 7-9.542 7-4.477 0-8.268-2.943-9.542-7z"/>
|
||||||
</svg>
|
</svg>
|
||||||
Details
|
Details
|
||||||
</button>
|
</button>
|
||||||
<button onclick="printerManager.editPrinter('${printer.id}')"
|
<button onclick="printerManager.editPrinter('${printer.id}')"
|
||||||
class="printer-action-btn btn-edit flex-1">
|
class="printer-action-btn btn-edit flex-1">
|
||||||
<svg class="w-4 h-4" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
<svg class="w-4 h-4" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M11 5H6a2 2 0 00-2 2v11a2 2 0 002 2h11a2 2 0 002-2v-5m-1.414-9.414a2 2 0 112.828 2.828L11.828 15H9v-2.828l8.586-8.586z"/>
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M11 5H6a2 2 0 00-2 2v11a2 2 0 002 2h11a2 2 0 002-2v-5m-1.414-9.414a2 2 0 112.828 2.828L11.828 15H9v-2.828l8.586-8.586z"/>
|
||||||
</svg>
|
</svg>
|
||||||
Bearbeiten
|
Bearbeiten
|
||||||
</button>
|
</button>
|
||||||
${this.getPrinterActionButton(printer)}
|
${this.getPrinterActionButton(printer)}
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
`;
|
||||||
`;
|
}
|
||||||
}
|
|
||||||
|
|
||||||
createPrinterListItem(printer) {
|
createPrinterListItem(printer) {
|
||||||
const statusClasses = this.getStatusClasses(printer.status);
|
const statusClasses = this.getStatusClasses(printer.status);
|
||||||
|
|
||||||
@ -1575,47 +1575,47 @@ class PrinterManager {
|
|||||||
}
|
}
|
||||||
|
|
||||||
getStatusClasses(status) {
|
getStatusClasses(status) {
|
||||||
const classes = {
|
const classes = {
|
||||||
'online': {
|
'online': {
|
||||||
container: 'status-online',
|
container: 'status-online',
|
||||||
iconBg: 'bg-green-100 dark:bg-green-900/30 text-green-600',
|
iconBg: 'bg-green-100 dark:bg-green-900/30 text-green-600',
|
||||||
badge: 'bg-green-100 text-green-800 dark:bg-green-900/30 dark:text-green-400'
|
badge: 'bg-green-100 text-green-800 dark:bg-green-900/30 dark:text-green-400'
|
||||||
},
|
},
|
||||||
'offline': {
|
'offline': {
|
||||||
container: 'status-offline',
|
container: 'status-offline',
|
||||||
iconBg: 'bg-red-100 dark:bg-red-900/30 text-red-600',
|
iconBg: 'bg-red-100 dark:bg-red-900/30 text-red-600',
|
||||||
badge: 'bg-red-100 text-red-800 dark:bg-red-900/30 dark:text-red-400'
|
badge: 'bg-red-100 text-red-800 dark:bg-red-900/30 dark:text-red-400'
|
||||||
},
|
},
|
||||||
'printing': {
|
'printing': {
|
||||||
container: 'status-printing',
|
container: 'status-printing',
|
||||||
iconBg: 'bg-blue-100 dark:bg-blue-900/30 text-blue-600',
|
iconBg: 'bg-blue-100 dark:bg-blue-900/30 text-blue-600',
|
||||||
badge: 'bg-blue-100 text-blue-800 dark:bg-blue-900/30 dark:text-blue-400'
|
badge: 'bg-blue-100 text-blue-800 dark:bg-blue-900/30 dark:text-blue-400'
|
||||||
},
|
},
|
||||||
'error': {
|
'error': {
|
||||||
container: 'status-error',
|
container: 'status-error',
|
||||||
iconBg: 'bg-orange-100 dark:bg-orange-900/30 text-orange-600',
|
iconBg: 'bg-orange-100 dark:bg-orange-900/30 text-orange-600',
|
||||||
badge: 'bg-orange-100 text-orange-800 dark:bg-orange-900/30 dark:text-orange-400'
|
badge: 'bg-orange-100 text-orange-800 dark:bg-orange-900/30 dark:text-orange-400'
|
||||||
},
|
},
|
||||||
'maintenance': {
|
'maintenance': {
|
||||||
container: 'status-maintenance',
|
container: 'status-maintenance',
|
||||||
iconBg: 'bg-purple-100 dark:bg-purple-900/30 text-purple-600',
|
iconBg: 'bg-purple-100 dark:bg-purple-900/30 text-purple-600',
|
||||||
badge: 'bg-purple-100 text-purple-800 dark:bg-purple-900/30 dark:text-purple-400'
|
badge: 'bg-purple-100 text-purple-800 dark:bg-purple-900/30 dark:text-purple-400'
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
return classes[status] || classes['offline'];
|
return classes[status] || classes['offline'];
|
||||||
}
|
}
|
||||||
|
|
||||||
getStatusIcon(status) {
|
getStatusIcon(status) {
|
||||||
const icons = {
|
const icons = {
|
||||||
'online': '<div class="w-3 h-3 bg-green-500 rounded-full"></div>',
|
'online': '<div class="w-3 h-3 bg-green-500 rounded-full"></div>',
|
||||||
'offline': '<div class="w-3 h-3 bg-red-500 rounded-full"></div>',
|
'offline': '<div class="w-3 h-3 bg-red-500 rounded-full"></div>',
|
||||||
'printing': '<div class="w-3 h-3 bg-blue-500 rounded-full status-pulse"></div>',
|
'printing': '<div class="w-3 h-3 bg-blue-500 rounded-full status-pulse"></div>',
|
||||||
'error': '<div class="w-3 h-3 bg-orange-500 rounded-full"></div>',
|
'error': '<div class="w-3 h-3 bg-orange-500 rounded-full"></div>',
|
||||||
'maintenance': '<div class="w-3 h-3 bg-purple-500 rounded-full"></div>'
|
'maintenance': '<div class="w-3 h-3 bg-purple-500 rounded-full"></div>'
|
||||||
};
|
};
|
||||||
return icons[status] || icons['offline'];
|
return icons[status] || icons['offline'];
|
||||||
}
|
}
|
||||||
|
|
||||||
getStatusText(status) {
|
getStatusText(status) {
|
||||||
const texts = {
|
const texts = {
|
||||||
'online': 'Online',
|
'online': 'Online',
|
||||||
@ -1629,7 +1629,7 @@ class PrinterManager {
|
|||||||
}
|
}
|
||||||
|
|
||||||
updateStatistics() {
|
updateStatistics() {
|
||||||
const stats = {
|
const stats = {
|
||||||
total: allPrinters.length,
|
total: allPrinters.length,
|
||||||
online: allPrinters.filter(p => ['online', 'idle'].includes(p.status)).length,
|
online: allPrinters.filter(p => ['online', 'idle'].includes(p.status)).length,
|
||||||
offline: allPrinters.filter(p => p.status === 'offline').length,
|
offline: allPrinters.filter(p => p.status === 'offline').length,
|
||||||
@ -1689,11 +1689,11 @@ class PrinterManager {
|
|||||||
}
|
}
|
||||||
|
|
||||||
populateFilterDropdowns() {
|
populateFilterDropdowns() {
|
||||||
// Populate location filter
|
// Populate location filter
|
||||||
const locationFilter = document.getElementById('filterLocation');
|
const locationFilter = document.getElementById('filterLocation');
|
||||||
const locations = [...new Set(allPrinters.map(p => p.location).filter(Boolean))];
|
const locations = [...new Set(allPrinters.map(p => p.location).filter(Boolean))];
|
||||||
locationFilter.innerHTML = '<option value="">Alle Standorte</option>' +
|
locationFilter.innerHTML = '<option value="">Alle Standorte</option>' +
|
||||||
locations.map(location => `<option value="${location}">${location}</option>`).join('');
|
locations.map(location => `<option value="${location}">${location}</option>`).join('');
|
||||||
|
|
||||||
// Populate model filter
|
// Populate model filter
|
||||||
const modelFilter = document.getElementById('filterModel');
|
const modelFilter = document.getElementById('filterModel');
|
||||||
@ -1781,9 +1781,9 @@ class PrinterManager {
|
|||||||
|
|
||||||
content.classList.remove('scale-100', 'opacity-100');
|
content.classList.remove('scale-100', 'opacity-100');
|
||||||
content.classList.add('scale-95', 'opacity-0');
|
content.classList.add('scale-95', 'opacity-0');
|
||||||
setTimeout(() => {
|
setTimeout(() => {
|
||||||
modal.classList.add('hidden');
|
modal.classList.add('hidden');
|
||||||
}, 200);
|
}, 200);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1845,7 +1845,7 @@ function toggleGridView(view) {
|
|||||||
gridBtn.classList.remove('text-mercedes-gray', 'hover:bg-mercedes-silver');
|
gridBtn.classList.remove('text-mercedes-gray', 'hover:bg-mercedes-silver');
|
||||||
listBtn.classList.remove('bg-mercedes-blue', 'text-white');
|
listBtn.classList.remove('bg-mercedes-blue', 'text-white');
|
||||||
listBtn.classList.add('text-mercedes-gray', 'hover:bg-mercedes-silver');
|
listBtn.classList.add('text-mercedes-gray', 'hover:bg-mercedes-silver');
|
||||||
} else {
|
} else {
|
||||||
listBtn.classList.add('bg-mercedes-blue', 'text-white');
|
listBtn.classList.add('bg-mercedes-blue', 'text-white');
|
||||||
listBtn.classList.remove('text-mercedes-gray', 'hover:bg-mercedes-silver');
|
listBtn.classList.remove('text-mercedes-gray', 'hover:bg-mercedes-silver');
|
||||||
gridBtn.classList.remove('bg-mercedes-blue', 'text-white');
|
gridBtn.classList.remove('bg-mercedes-blue', 'text-white');
|
||||||
|
@ -261,7 +261,7 @@
|
|||||||
|
|
||||||
for (let [key, value] of formData.entries()) {
|
for (let [key, value] of formData.entries()) {
|
||||||
if (key !== 'avatar') { // Don't store file data
|
if (key !== 'avatar') { // Don't store file data
|
||||||
originalFormData[key] = value;
|
originalFormData[key] = value;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -586,7 +586,7 @@
|
|||||||
|
|
||||||
for (let [key, value] of formData.entries()) {
|
for (let [key, value] of formData.entries()) {
|
||||||
if (key !== 'avatar') {
|
if (key !== 'avatar') {
|
||||||
profileData[key] = value;
|
profileData[key] = value;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user