1020 lines
28 KiB
HTML
1020 lines
28 KiB
HTML
|
|
<!-- Tools Section Template for Settings -->
|
||
|
|
<!-- This is loaded via HTMX into the settings page -->
|
||
|
|
|
||
|
|
<div class="tools-section" id="tools-container">
|
||
|
|
<!-- Desktop Only Warning (shown via JS if not in Tauri) -->
|
||
|
|
<div class="tools-warning" id="desktop-warning" style="display: none;">
|
||
|
|
<div class="warning-icon">⚠️</div>
|
||
|
|
<div class="warning-content">
|
||
|
|
<h4>Desktop Mode Recommended</h4>
|
||
|
|
<p>Some tools require the desktop application for full functionality.</p>
|
||
|
|
</div>
|
||
|
|
</div>
|
||
|
|
|
||
|
|
<!-- Drive Cleaner Card -->
|
||
|
|
<div class="setting-card">
|
||
|
|
<h3 class="card-title">
|
||
|
|
<span class="card-icon">🧹</span>
|
||
|
|
Drive Cleaner
|
||
|
|
</h3>
|
||
|
|
<p class="card-description">
|
||
|
|
Remove temporary files, browser cache, and other junk to free up disk space.
|
||
|
|
</p>
|
||
|
|
|
||
|
|
<!-- Disk Info -->
|
||
|
|
<div class="disk-info-section">
|
||
|
|
<div class="section-header-row">
|
||
|
|
<h4>Disk Space</h4>
|
||
|
|
<button class="btn btn-small" id="btn-analyze-disk"
|
||
|
|
hx-get="/api/v1/desktop/disk-info"
|
||
|
|
hx-target="#disk-info-container"
|
||
|
|
hx-indicator="#analyze-spinner">
|
||
|
|
<span id="analyze-spinner" class="htmx-indicator spinner"></span>
|
||
|
|
🔍 Analyze
|
||
|
|
</button>
|
||
|
|
</div>
|
||
|
|
<div id="disk-info-container" class="disk-info-container">
|
||
|
|
<p class="no-data">Click "Analyze" to scan your disks</p>
|
||
|
|
</div>
|
||
|
|
</div>
|
||
|
|
|
||
|
|
<!-- Cleanup Categories -->
|
||
|
|
<div class="cleanup-categories">
|
||
|
|
<h4>Select items to clean:</h4>
|
||
|
|
<div class="category-grid">
|
||
|
|
<label class="category-item">
|
||
|
|
<input type="checkbox" class="cleanup-category" value="temp_files" checked>
|
||
|
|
<span class="category-icon">📁</span>
|
||
|
|
<span class="category-name">Temporary Files</span>
|
||
|
|
<span class="category-desc">System and app temp files</span>
|
||
|
|
</label>
|
||
|
|
<label class="category-item">
|
||
|
|
<input type="checkbox" class="cleanup-category" value="browser_cache">
|
||
|
|
<span class="category-icon">🌐</span>
|
||
|
|
<span class="category-name">Browser Cache</span>
|
||
|
|
<span class="category-desc">Chrome, Edge, Brave, Firefox</span>
|
||
|
|
</label>
|
||
|
|
<label class="category-item">
|
||
|
|
<input type="checkbox" class="cleanup-category" value="recycle_bin">
|
||
|
|
<span class="category-icon">🗑️</span>
|
||
|
|
<span class="category-name">Recycle Bin</span>
|
||
|
|
<span class="category-desc">Empty trash/recycle bin</span>
|
||
|
|
</label>
|
||
|
|
<label class="category-item">
|
||
|
|
<input type="checkbox" class="cleanup-category" value="thumbnails">
|
||
|
|
<span class="category-icon">🖼️</span>
|
||
|
|
<span class="category-name">Thumbnails</span>
|
||
|
|
<span class="category-desc">Image preview cache</span>
|
||
|
|
</label>
|
||
|
|
<label class="category-item">
|
||
|
|
<input type="checkbox" class="cleanup-category" value="logs">
|
||
|
|
<span class="category-icon">📋</span>
|
||
|
|
<span class="category-name">Old Logs</span>
|
||
|
|
<span class="category-desc">Log files older than 7 days</span>
|
||
|
|
</label>
|
||
|
|
<label class="category-item">
|
||
|
|
<input type="checkbox" class="cleanup-category" value="update_cache">
|
||
|
|
<span class="category-icon">🔄</span>
|
||
|
|
<span class="category-name">Update Cache</span>
|
||
|
|
<span class="category-desc">Windows Update downloads</span>
|
||
|
|
</label>
|
||
|
|
</div>
|
||
|
|
</div>
|
||
|
|
|
||
|
|
<!-- Cleanup Progress -->
|
||
|
|
<div class="progress-section" id="cleanup-progress-section" style="display: none;">
|
||
|
|
<div class="progress-bar-container">
|
||
|
|
<div class="progress-bar" id="cleanup-progress-bar"></div>
|
||
|
|
</div>
|
||
|
|
<p class="progress-text" id="cleanup-progress-text">Preparing...</p>
|
||
|
|
</div>
|
||
|
|
|
||
|
|
<!-- Cleanup Results -->
|
||
|
|
<div id="cleanup-results"></div>
|
||
|
|
|
||
|
|
<!-- Cleanup Actions -->
|
||
|
|
<div class="card-actions">
|
||
|
|
<button class="btn btn-primary" id="btn-clean-all"
|
||
|
|
hx-post="/api/v1/desktop/cleanup"
|
||
|
|
hx-vals='js:{categories: getSelectedCategories()}'
|
||
|
|
hx-target="#cleanup-results"
|
||
|
|
hx-indicator="#cleanup-spinner">
|
||
|
|
<span id="cleanup-spinner" class="htmx-indicator spinner"></span>
|
||
|
|
🧹 Clean Selected
|
||
|
|
</button>
|
||
|
|
<button class="btn btn-secondary" id="btn-empty-recycle"
|
||
|
|
hx-post="/api/v1/desktop/cleanup"
|
||
|
|
hx-vals='{"categories": ["recycle_bin"]}'
|
||
|
|
hx-target="#cleanup-results">
|
||
|
|
🗑️ Empty Recycle Bin
|
||
|
|
</button>
|
||
|
|
</div>
|
||
|
|
</div>
|
||
|
|
|
||
|
|
<!-- Antivirus Card -->
|
||
|
|
<div class="setting-card">
|
||
|
|
<h3 class="card-title">
|
||
|
|
<span class="card-icon">🛡️</span>
|
||
|
|
Antivirus
|
||
|
|
</h3>
|
||
|
|
<p class="card-description">
|
||
|
|
Scan your system for threats using ClamAV open-source antivirus engine.
|
||
|
|
</p>
|
||
|
|
|
||
|
|
<!-- Protection Status -->
|
||
|
|
<div id="protection-status" class="protection-status"
|
||
|
|
hx-get="/api/v1/security/status"
|
||
|
|
hx-trigger="load, every 30s"
|
||
|
|
hx-swap="innerHTML">
|
||
|
|
<div class="status-loading">Loading protection status...</div>
|
||
|
|
</div>
|
||
|
|
|
||
|
|
<!-- Windows Defender Toggle -->
|
||
|
|
<div class="setting-row defender-row">
|
||
|
|
<div class="setting-info">
|
||
|
|
<div class="setting-label">🪟 Use General Bots Instead of Windows Defender</div>
|
||
|
|
<div class="setting-hint">
|
||
|
|
Disable Windows Defender and use General Bots protection (requires admin)
|
||
|
|
</div>
|
||
|
|
</div>
|
||
|
|
<div class="setting-control">
|
||
|
|
<label class="toggle-switch">
|
||
|
|
<input type="checkbox" id="toggle-defender"
|
||
|
|
hx-post="/api/v1/security/defender/toggle"
|
||
|
|
hx-trigger="change"
|
||
|
|
hx-swap="none">
|
||
|
|
<span class="toggle-slider"></span>
|
||
|
|
</label>
|
||
|
|
</div>
|
||
|
|
</div>
|
||
|
|
|
||
|
|
<!-- Scan Progress -->
|
||
|
|
<div class="progress-section" id="scan-progress-section" style="display: none;">
|
||
|
|
<div class="progress-bar-container">
|
||
|
|
<div class="progress-bar" id="scan-progress-bar"></div>
|
||
|
|
</div>
|
||
|
|
<p class="progress-text" id="scan-progress-text">Scanning...</p>
|
||
|
|
</div>
|
||
|
|
|
||
|
|
<!-- Threats List -->
|
||
|
|
<div id="threats-list" class="threats-list"
|
||
|
|
hx-get="/api/v1/security/threats"
|
||
|
|
hx-trigger="load"
|
||
|
|
hx-swap="innerHTML">
|
||
|
|
</div>
|
||
|
|
|
||
|
|
<!-- Scan Actions -->
|
||
|
|
<div class="card-actions">
|
||
|
|
<button class="btn btn-primary" id="btn-quick-scan"
|
||
|
|
hx-post="/api/v1/security/scan"
|
||
|
|
hx-vals='{"scan_type": "quick"}'
|
||
|
|
hx-target="#scan-progress-section"
|
||
|
|
hx-swap="outerHTML">
|
||
|
|
⚡ Quick Scan
|
||
|
|
</button>
|
||
|
|
<button class="btn btn-secondary" id="btn-full-scan"
|
||
|
|
hx-post="/api/v1/security/scan"
|
||
|
|
hx-vals='{"scan_type": "full"}'
|
||
|
|
hx-target="#scan-progress-section">
|
||
|
|
🔍 Full Scan
|
||
|
|
</button>
|
||
|
|
<button class="btn btn-secondary" id="btn-update-definitions"
|
||
|
|
hx-post="/api/v1/security/definitions/update"
|
||
|
|
hx-swap="none">
|
||
|
|
📥 Update Definitions
|
||
|
|
</button>
|
||
|
|
</div>
|
||
|
|
</div>
|
||
|
|
|
||
|
|
<!-- Windows Optimizer Card -->
|
||
|
|
<div class="setting-card">
|
||
|
|
<h3 class="card-title">
|
||
|
|
<span class="card-icon">⚡</span>
|
||
|
|
Optimize Windows
|
||
|
|
</h3>
|
||
|
|
<p class="card-description">
|
||
|
|
Optimize your Windows system for better performance using
|
||
|
|
<a href="https://github.com/Metaljisawa/OptimizationWindowsV1" target="_blank">OptimizationWindowsV1</a>.
|
||
|
|
</p>
|
||
|
|
|
||
|
|
<!-- Optimization Tasks -->
|
||
|
|
<div class="optimization-tasks">
|
||
|
|
<div class="task-grid">
|
||
|
|
<div class="task-item">
|
||
|
|
<span class="task-icon">💾</span>
|
||
|
|
<div class="task-info">
|
||
|
|
<span class="task-name">Defragment Disk</span>
|
||
|
|
<span class="task-desc">Optimize disk for faster access</span>
|
||
|
|
</div>
|
||
|
|
<button class="btn btn-small" id="btn-defrag"
|
||
|
|
hx-post="/api/v1/desktop/optimize"
|
||
|
|
hx-vals='{"tasks": ["defragment_disk"]}'
|
||
|
|
hx-swap="none">
|
||
|
|
Run
|
||
|
|
</button>
|
||
|
|
</div>
|
||
|
|
<div class="task-item">
|
||
|
|
<span class="task-icon">🧠</span>
|
||
|
|
<div class="task-info">
|
||
|
|
<span class="task-name">Clear Memory</span>
|
||
|
|
<span class="task-desc">Free up RAM for better performance</span>
|
||
|
|
</div>
|
||
|
|
<button class="btn btn-small" id="btn-clear-memory"
|
||
|
|
hx-post="/api/v1/desktop/optimize"
|
||
|
|
hx-vals='{"tasks": ["clear_memory"]}'
|
||
|
|
hx-swap="none">
|
||
|
|
Run
|
||
|
|
</button>
|
||
|
|
</div>
|
||
|
|
<div class="task-item">
|
||
|
|
<span class="task-icon">🚀</span>
|
||
|
|
<div class="task-info">
|
||
|
|
<span class="task-name">Optimize Services</span>
|
||
|
|
<span class="task-desc">Disable unnecessary services</span>
|
||
|
|
</div>
|
||
|
|
<button class="btn btn-small" id="btn-optimize-services"
|
||
|
|
hx-post="/api/v1/desktop/optimize"
|
||
|
|
hx-vals='{"tasks": ["optimize_services"]}'
|
||
|
|
hx-swap="none">
|
||
|
|
Run
|
||
|
|
</button>
|
||
|
|
</div>
|
||
|
|
<div class="task-item">
|
||
|
|
<span class="task-icon">🎯</span>
|
||
|
|
<div class="task-info">
|
||
|
|
<span class="task-name">Startup Programs</span>
|
||
|
|
<span class="task-desc">Manage startup applications</span>
|
||
|
|
</div>
|
||
|
|
<button class="btn btn-small" id="btn-startup"
|
||
|
|
hx-post="/api/v1/desktop/optimize"
|
||
|
|
hx-vals='{"tasks": ["disable_startup_programs"]}'
|
||
|
|
hx-swap="none">
|
||
|
|
Run
|
||
|
|
</button>
|
||
|
|
</div>
|
||
|
|
</div>
|
||
|
|
</div>
|
||
|
|
|
||
|
|
<!-- Optimization Actions -->
|
||
|
|
<div class="card-actions">
|
||
|
|
<button class="btn btn-primary" id="btn-optimize-windows"
|
||
|
|
hx-post="/api/v1/desktop/optimize"
|
||
|
|
hx-vals='{"tasks": ["all"]}'
|
||
|
|
hx-swap="none"
|
||
|
|
hx-indicator="#optimize-spinner">
|
||
|
|
<span id="optimize-spinner" class="htmx-indicator spinner"></span>
|
||
|
|
⚡ Run Full Optimization
|
||
|
|
</button>
|
||
|
|
<button class="btn btn-secondary" id="btn-run-script"
|
||
|
|
hx-post="/api/v1/desktop/optimize/script"
|
||
|
|
hx-swap="none">
|
||
|
|
📜 Run External Script
|
||
|
|
</button>
|
||
|
|
</div>
|
||
|
|
</div>
|
||
|
|
|
||
|
|
<!-- Software Installation Card -->
|
||
|
|
<div class="setting-card">
|
||
|
|
<h3 class="card-title">
|
||
|
|
<span class="card-icon">📦</span>
|
||
|
|
Install Software
|
||
|
|
</h3>
|
||
|
|
<p class="card-description">
|
||
|
|
Quickly install recommended software on your system.
|
||
|
|
</p>
|
||
|
|
|
||
|
|
<!-- Software List -->
|
||
|
|
<div class="software-list">
|
||
|
|
<div class="software-item">
|
||
|
|
<div class="software-icon">🦁</div>
|
||
|
|
<div class="software-info">
|
||
|
|
<span class="software-name">Brave Browser</span>
|
||
|
|
<span class="software-desc">Privacy-focused browser with built-in ad blocker</span>
|
||
|
|
</div>
|
||
|
|
<button class="btn btn-primary btn-small" id="btn-install-brave"
|
||
|
|
hx-post="/api/v1/desktop/install/brave"
|
||
|
|
hx-target="#install-progress-section"
|
||
|
|
hx-swap="outerHTML">
|
||
|
|
Install
|
||
|
|
</button>
|
||
|
|
</div>
|
||
|
|
</div>
|
||
|
|
|
||
|
|
<!-- Install Progress -->
|
||
|
|
<div class="progress-section" id="install-progress-section" style="display: none;">
|
||
|
|
<div class="progress-bar-container">
|
||
|
|
<div class="progress-bar" id="install-progress-bar"></div>
|
||
|
|
</div>
|
||
|
|
<p class="progress-text" id="install-progress-text">Installing...</p>
|
||
|
|
</div>
|
||
|
|
</div>
|
||
|
|
|
||
|
|
<!-- Notification -->
|
||
|
|
<div class="notification" id="tools-notification"></div>
|
||
|
|
</div>
|
||
|
|
|
||
|
|
<style>
|
||
|
|
/* Tools Section Styles */
|
||
|
|
.tools-section {
|
||
|
|
max-width: 900px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.tools-warning {
|
||
|
|
display: flex;
|
||
|
|
align-items: flex-start;
|
||
|
|
gap: 16px;
|
||
|
|
padding: 16px 20px;
|
||
|
|
background: rgba(245, 158, 11, 0.1);
|
||
|
|
border: 1px solid rgba(245, 158, 11, 0.3);
|
||
|
|
border-radius: 8px;
|
||
|
|
margin-bottom: 24px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.warning-icon {
|
||
|
|
font-size: 24px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.warning-content h4 {
|
||
|
|
margin-bottom: 4px;
|
||
|
|
color: #f59e0b;
|
||
|
|
}
|
||
|
|
|
||
|
|
.warning-content p {
|
||
|
|
font-size: 13px;
|
||
|
|
color: var(--text-secondary, #94a3b8);
|
||
|
|
}
|
||
|
|
|
||
|
|
.card-title {
|
||
|
|
display: flex;
|
||
|
|
align-items: center;
|
||
|
|
gap: 10px;
|
||
|
|
font-size: 18px;
|
||
|
|
font-weight: 600;
|
||
|
|
margin-bottom: 8px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.card-icon {
|
||
|
|
font-size: 24px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.card-description {
|
||
|
|
color: var(--text-secondary, #94a3b8);
|
||
|
|
font-size: 14px;
|
||
|
|
margin-bottom: 24px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.card-description a {
|
||
|
|
color: var(--accent-color, #3b82f6);
|
||
|
|
text-decoration: none;
|
||
|
|
}
|
||
|
|
|
||
|
|
.card-description a:hover {
|
||
|
|
text-decoration: underline;
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Disk Info */
|
||
|
|
.disk-info-section {
|
||
|
|
margin-bottom: 24px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.section-header-row {
|
||
|
|
display: flex;
|
||
|
|
justify-content: space-between;
|
||
|
|
align-items: center;
|
||
|
|
margin-bottom: 16px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.section-header-row h4 {
|
||
|
|
font-size: 14px;
|
||
|
|
font-weight: 600;
|
||
|
|
}
|
||
|
|
|
||
|
|
.disk-info-container {
|
||
|
|
background: var(--bg-tertiary, #334155);
|
||
|
|
border-radius: 8px;
|
||
|
|
padding: 16px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.disk-item {
|
||
|
|
margin-bottom: 16px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.disk-item:last-child {
|
||
|
|
margin-bottom: 0;
|
||
|
|
}
|
||
|
|
|
||
|
|
.disk-header {
|
||
|
|
display: flex;
|
||
|
|
justify-content: space-between;
|
||
|
|
margin-bottom: 8px;
|
||
|
|
font-size: 14px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.disk-name {
|
||
|
|
font-weight: 500;
|
||
|
|
}
|
||
|
|
|
||
|
|
.disk-usage {
|
||
|
|
color: var(--text-secondary, #94a3b8);
|
||
|
|
}
|
||
|
|
|
||
|
|
.disk-bar {
|
||
|
|
height: 8px;
|
||
|
|
background: var(--bg-secondary, #1e293b);
|
||
|
|
border-radius: 4px;
|
||
|
|
overflow: hidden;
|
||
|
|
}
|
||
|
|
|
||
|
|
.disk-bar-fill {
|
||
|
|
height: 100%;
|
||
|
|
border-radius: 4px;
|
||
|
|
transition: width 0.3s ease;
|
||
|
|
}
|
||
|
|
|
||
|
|
.disk-bar-fill.normal {
|
||
|
|
background: linear-gradient(90deg, #22c55e, #4ade80);
|
||
|
|
}
|
||
|
|
|
||
|
|
.disk-bar-fill.warning {
|
||
|
|
background: linear-gradient(90deg, #f59e0b, #fbbf24);
|
||
|
|
}
|
||
|
|
|
||
|
|
.disk-bar-fill.critical {
|
||
|
|
background: linear-gradient(90deg, #ef4444, #f87171);
|
||
|
|
}
|
||
|
|
|
||
|
|
.disk-footer {
|
||
|
|
display: flex;
|
||
|
|
justify-content: space-between;
|
||
|
|
margin-top: 8px;
|
||
|
|
font-size: 12px;
|
||
|
|
color: var(--text-secondary, #94a3b8);
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Cleanup Categories */
|
||
|
|
.cleanup-categories h4 {
|
||
|
|
font-size: 14px;
|
||
|
|
font-weight: 600;
|
||
|
|
margin-bottom: 16px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.category-grid {
|
||
|
|
display: grid;
|
||
|
|
grid-template-columns: repeat(auto-fill, minmax(200px, 1fr));
|
||
|
|
gap: 12px;
|
||
|
|
margin-bottom: 24px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.category-item {
|
||
|
|
display: flex;
|
||
|
|
align-items: flex-start;
|
||
|
|
gap: 12px;
|
||
|
|
padding: 12px;
|
||
|
|
background: var(--bg-tertiary, #334155);
|
||
|
|
border-radius: 8px;
|
||
|
|
cursor: pointer;
|
||
|
|
transition: all 0.2s;
|
||
|
|
border: 2px solid transparent;
|
||
|
|
}
|
||
|
|
|
||
|
|
.category-item:hover {
|
||
|
|
background: var(--bg-secondary, #1e293b);
|
||
|
|
}
|
||
|
|
|
||
|
|
.category-item:has(input:checked) {
|
||
|
|
border-color: var(--accent-color, #3b82f6);
|
||
|
|
background: rgba(59, 130, 246, 0.1);
|
||
|
|
}
|
||
|
|
|
||
|
|
.category-item input {
|
||
|
|
margin-top: 4px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.category-icon {
|
||
|
|
font-size: 20px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.category-name {
|
||
|
|
display: block;
|
||
|
|
font-weight: 500;
|
||
|
|
font-size: 14px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.category-desc {
|
||
|
|
display: block;
|
||
|
|
font-size: 12px;
|
||
|
|
color: var(--text-secondary, #94a3b8);
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Progress Section */
|
||
|
|
.progress-section {
|
||
|
|
margin: 20px 0;
|
||
|
|
padding: 16px;
|
||
|
|
background: var(--bg-tertiary, #334155);
|
||
|
|
border-radius: 8px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.progress-bar-container {
|
||
|
|
height: 8px;
|
||
|
|
background: var(--bg-secondary, #1e293b);
|
||
|
|
border-radius: 4px;
|
||
|
|
overflow: hidden;
|
||
|
|
margin-bottom: 12px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.progress-bar {
|
||
|
|
height: 100%;
|
||
|
|
background: linear-gradient(90deg, var(--accent-color, #3b82f6), #60a5fa);
|
||
|
|
border-radius: 4px;
|
||
|
|
width: 0%;
|
||
|
|
transition: width 0.3s ease;
|
||
|
|
}
|
||
|
|
|
||
|
|
.progress-text {
|
||
|
|
font-size: 13px;
|
||
|
|
color: var(--text-secondary, #94a3b8);
|
||
|
|
text-align: center;
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Cleanup Results */
|
||
|
|
.cleanup-stats {
|
||
|
|
display: grid;
|
||
|
|
grid-template-columns: repeat(3, 1fr);
|
||
|
|
gap: 16px;
|
||
|
|
margin-bottom: 16px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.cleanup-stats .stat-item {
|
||
|
|
text-align: center;
|
||
|
|
padding: 16px;
|
||
|
|
background: var(--bg-tertiary, #334155);
|
||
|
|
border-radius: 8px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.cleanup-stats .stat-value {
|
||
|
|
display: block;
|
||
|
|
font-size: 24px;
|
||
|
|
font-weight: 700;
|
||
|
|
color: var(--accent-color, #3b82f6);
|
||
|
|
}
|
||
|
|
|
||
|
|
.cleanup-stats .stat-label {
|
||
|
|
display: block;
|
||
|
|
font-size: 12px;
|
||
|
|
color: var(--text-secondary, #94a3b8);
|
||
|
|
margin-top: 4px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.cleanup-errors {
|
||
|
|
padding: 12px;
|
||
|
|
background: rgba(239, 68, 68, 0.1);
|
||
|
|
border: 1px solid rgba(239, 68, 68, 0.3);
|
||
|
|
border-radius: 8px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.cleanup-errors h4 {
|
||
|
|
color: #ef4444;
|
||
|
|
font-size: 13px;
|
||
|
|
margin-bottom: 8px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.cleanup-errors ul {
|
||
|
|
font-size: 12px;
|
||
|
|
color: var(--text-secondary, #94a3b8);
|
||
|
|
padding-left: 20px;
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Protection Status */
|
||
|
|
.protection-status {
|
||
|
|
margin-bottom: 24px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.status-grid {
|
||
|
|
display: grid;
|
||
|
|
grid-template-columns: repeat(auto-fill, minmax(180px, 1fr));
|
||
|
|
gap: 12px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.status-item {
|
||
|
|
display: flex;
|
||
|
|
flex-direction: column;
|
||
|
|
align-items: center;
|
||
|
|
padding: 16px;
|
||
|
|
background: var(--bg-tertiary, #334155);
|
||
|
|
border-radius: 8px;
|
||
|
|
text-align: center;
|
||
|
|
}
|
||
|
|
|
||
|
|
.status-item.active {
|
||
|
|
border: 1px solid rgba(34, 197, 94, 0.3);
|
||
|
|
background: rgba(34, 197, 94, 0.1);
|
||
|
|
}
|
||
|
|
|
||
|
|
.status-item.inactive {
|
||
|
|
border: 1px solid rgba(239, 68, 68, 0.3);
|
||
|
|
background: rgba(239, 68, 68, 0.1);
|
||
|
|
}
|
||
|
|
|
||
|
|
.status-icon {
|
||
|
|
font-size: 24px;
|
||
|
|
margin-bottom: 8px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.status-label {
|
||
|
|
font-size: 12px;
|
||
|
|
color: var(--text-secondary, #94a3b8);
|
||
|
|
margin-bottom: 4px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.status-value {
|
||
|
|
font-weight: 600;
|
||
|
|
font-size: 14px;
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Defender Row */
|
||
|
|
.defender-row {
|
||
|
|
padding: 16px;
|
||
|
|
background: var(--bg-tertiary, #334155);
|
||
|
|
border-radius: 8px;
|
||
|
|
margin-bottom: 24px;
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Threats List */
|
||
|
|
.threats-list {
|
||
|
|
margin-bottom: 24px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.no-threats {
|
||
|
|
text-align: center;
|
||
|
|
padding: 32px;
|
||
|
|
background: var(--bg-tertiary, #334155);
|
||
|
|
border-radius: 8px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.no-threats-icon {
|
||
|
|
font-size: 48px;
|
||
|
|
display: block;
|
||
|
|
margin-bottom: 12px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.threat-item {
|
||
|
|
display: flex;
|
||
|
|
align-items: center;
|
||
|
|
gap: 16px;
|
||
|
|
padding: 16px;
|
||
|
|
background: var(--bg-tertiary, #334155);
|
||
|
|
border-radius: 8px;
|
||
|
|
margin-bottom: 8px;
|
||
|
|
border-left: 4px solid transparent;
|
||
|
|
}
|
||
|
|
|
||
|
|
.threat-item.severity-critical {
|
||
|
|
border-left-color: #dc2626;
|
||
|
|
background: rgba(220, 38, 38, 0.1);
|
||
|
|
}
|
||
|
|
|
||
|
|
.threat-item.severity-high {
|
||
|
|
border-left-color: #ea580c;
|
||
|
|
background: rgba(234, 88, 12, 0.1);
|
||
|
|
}
|
||
|
|
|
||
|
|
.threat-item.severity-medium {
|
||
|
|
border-left-color: #ca8a04;
|
||
|
|
background: rgba(202, 138, 4, 0.1);
|
||
|
|
}
|
||
|
|
|
||
|
|
.threat-item.severity-low {
|
||
|
|
border-left-color: #16a34a;
|
||
|
|
}
|
||
|
|
|
||
|
|
.threat-icon {
|
||
|
|
font-size: 24px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.threat-info {
|
||
|
|
flex: 1;
|
||
|
|
}
|
||
|
|
|
||
|
|
.threat-name {
|
||
|
|
font-weight: 600;
|
||
|
|
font-size: 14px;
|
||
|
|
margin-bottom: 4px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.threat-path {
|
||
|
|
font-size: 12px;
|
||
|
|
color: var(--text-secondary, #94a3b8);
|
||
|
|
word-break: break-all;
|
||
|
|
}
|
||
|
|
|
||
|
|
.threat-type {
|
||
|
|
display: inline-block;
|
||
|
|
font-size: 11px;
|
||
|
|
padding: 2px 8px;
|
||
|
|
background: var(--bg-secondary, #1e293b);
|
||
|
|
border-radius: 4px;
|
||
|
|
margin-top: 4px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.threat-actions {
|
||
|
|
display: flex;
|
||
|
|
gap: 8px;
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Optimization Tasks */
|
||
|
|
.optimization-tasks {
|
||
|
|
margin-bottom: 24px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.task-grid {
|
||
|
|
display: flex;
|
||
|
|
flex-direction: column;
|
||
|
|
gap: 12px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.task-item {
|
||
|
|
display: flex;
|
||
|
|
align-items: center;
|
||
|
|
gap: 16px;
|
||
|
|
padding: 16px;
|
||
|
|
background: var(--bg-tertiary, #334155);
|
||
|
|
border-radius: 8px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.task-icon {
|
||
|
|
font-size: 24px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.task-info {
|
||
|
|
flex: 1;
|
||
|
|
}
|
||
|
|
|
||
|
|
.task-name {
|
||
|
|
display: block;
|
||
|
|
font-weight: 500;
|
||
|
|
font-size: 14px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.task-desc {
|
||
|
|
display: block;
|
||
|
|
font-size: 12px;
|
||
|
|
color: var(--text-secondary, #94a3b8);
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Software List */
|
||
|
|
.software-list {
|
||
|
|
margin-bottom: 24px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.software-item {
|
||
|
|
display: flex;
|
||
|
|
align-items: center;
|
||
|
|
gap: 16px;
|
||
|
|
padding: 16px;
|
||
|
|
background: var(--bg-tertiary, #334155);
|
||
|
|
border-radius: 8px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.software-icon {
|
||
|
|
font-size: 32px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.software-info {
|
||
|
|
flex: 1;
|
||
|
|
}
|
||
|
|
|
||
|
|
.software-name {
|
||
|
|
display: block;
|
||
|
|
font-weight: 600;
|
||
|
|
font-size: 15px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.software-desc {
|
||
|
|
display: block;
|
||
|
|
font-size: 13px;
|
||
|
|
color: var(--text-secondary, #94a3b8);
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Card Actions */
|
||
|
|
.card-actions {
|
||
|
|
display: flex;
|
||
|
|
gap: 12px;
|
||
|
|
flex-wrap: wrap;
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Buttons */
|
||
|
|
.btn {
|
||
|
|
display: inline-flex;
|
||
|
|
align-items: center;
|
||
|
|
justify-content: center;
|
||
|
|
gap: 8px;
|
||
|
|
padding: 10px 18px;
|
||
|
|
border: none;
|
||
|
|
border-radius: 8px;
|
||
|
|
font-size: 14px;
|
||
|
|
font-weight: 500;
|
||
|
|
cursor: pointer;
|
||
|
|
transition: all 0.2s;
|
||
|
|
}
|
||
|
|
|
||
|
|
.btn-primary {
|
||
|
|
background: var(--accent-color, #3b82f6);
|
||
|
|
color: white;
|
||
|
|
}
|
||
|
|
|
||
|
|
.btn-primary:hover {
|
||
|
|
background: var(--accent-hover, #2563eb);
|
||
|
|
}
|
||
|
|
|
||
|
|
.btn-secondary {
|
||
|
|
background: var(--bg-tertiary, #334155);
|
||
|
|
color: var(--text-primary, #f1f5f9);
|
||
|
|
}
|
||
|
|
|
||
|
|
.btn-secondary:hover {
|
||
|
|
background: var(--border-color, #475569);
|
||
|
|
}
|
||
|
|
|
||
|
|
.btn-danger {
|
||
|
|
background: #ef4444;
|
||
|
|
color: white;
|
||
|
|
}
|
||
|
|
|
||
|
|
.btn-danger:hover {
|
||
|
|
background: #dc2626;
|
||
|
|
}
|
||
|
|
|
||
|
|
.btn-small {
|
||
|
|
padding: 6px 12px;
|
||
|
|
font-size: 13px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.btn:disabled {
|
||
|
|
opacity: 0.5;
|
||
|
|
cursor: not-allowed;
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Spinner */
|
||
|
|
.spinner {
|
||
|
|
width: 16px;
|
||
|
|
height: 16px;
|
||
|
|
border: 2px solid transparent;
|
||
|
|
border-top-color: currentColor;
|
||
|
|
border-radius: 50%;
|
||
|
|
animation: spin 0.8s linear infinite;
|
||
|
|
}
|
||
|
|
|
||
|
|
.htmx-indicator {
|
||
|
|
display: none;
|
||
|
|
}
|
||
|
|
|
||
|
|
.htmx-request .htmx-indicator {
|
||
|
|
display: inline-block;
|
||
|
|
}
|
||
|
|
|
||
|
|
@keyframes spin {
|
||
|
|
to {
|
||
|
|
transform: rotate(360deg);
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Toggle Switch */
|
||
|
|
.toggle-switch {
|
||
|
|
position: relative;
|
||
|
|
display: inline-block;
|
||
|
|
width: 48px;
|
||
|
|
height: 26px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.toggle-switch input {
|
||
|
|
opacity: 0;
|
||
|
|
width: 0;
|
||
|
|
height: 0;
|
||
|
|
}
|
||
|
|
|
||
|
|
.toggle-slider {
|
||
|
|
position: absolute;
|
||
|
|
cursor: pointer;
|
||
|
|
top: 0;
|
||
|
|
left: 0;
|
||
|
|
right: 0;
|
||
|
|
bottom: 0;
|
||
|
|
background: var(--text-secondary, #94a3b8);
|
||
|
|
transition: 0.3s;
|
||
|
|
border-radius: 26px;
|
||
|
|
}
|
||
|
|
|
||
|
|
.toggle-slider:before {
|
||
|
|
position: absolute;
|
||
|
|
content: "";
|
||
|
|
height: 20px;
|
||
|
|
width: 20px;
|
||
|
|
left: 3px;
|
||
|
|
bottom: 3px;
|
||
|
|
background: white;
|
||
|
|
transition: 0.3s;
|
||
|
|
border-radius: 50%;
|
||
|
|
}
|
||
|
|
|
||
|
|
.toggle-switch input:checked + .toggle-slider {
|
||
|
|
background: var(--accent-color, #3b82f6);
|
||
|
|
}
|
||
|
|
|
||
|
|
.toggle-switch input:checked + .toggle-slider:before {
|
||
|
|
transform: translateX(22px);
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Notification */
|
||
|
|
.notification {
|
||
|
|
position: fixed;
|
||
|
|
bottom: 20px;
|
||
|
|
right: 20px;
|
||
|
|
padding: 14px 24px;
|
||
|
|
background: var(--bg-tertiary, #334155);
|
||
|
|
border-radius: 8px;
|
||
|
|
box-shadow: 0 4px 12px rgba(0, 0, 0, 0.3);
|
||
|
|
transform: translateX(150%);
|
||
|
|
transition: transform 0.3s ease;
|
||
|
|
z-index: 1000;
|
||
|
|
}
|
||
|
|
|
||
|
|
.notification.show {
|
||
|
|
transform: translateX(0);
|
||
|
|
}
|
||
|
|
|
||
|
|
.notification.success {
|
||
|
|
border-left: 4px solid #22c55e;
|
||
|
|
}
|
||
|
|
|
||
|
|
.notification.error {
|
||
|
|
border-left: 4px solid #ef4444;
|
||
|
|
}
|
||
|
|
|
||
|
|
.notification.warning {
|
||
|
|
border-left: 4px solid #f59e0b;
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Responsive */
|
||
|
|
@media (max-width: 768px) {
|
||
|
|
.category-grid {
|
||
|
|
grid-template-columns: 1fr;
|
||
|
|
}
|
||
|
|
|
||
|
|
.status-grid {
|
||
|
|
grid-template-columns: repeat(2, 1fr);
|
||
|
|
}
|
||
|
|
|
||
|
|
.cleanup-stats {
|
||
|
|
grid-template-columns: 1fr;
|
||
|
|
}
|
||
|
|
|
||
|
|
.card-actions {
|
||
|
|
flex-direction: column;
|
||
|
|
}
|
||
|
|
|
||
|
|
.card-actions .btn {
|
||
|
|
width: 100%;
|
||
|
|
}
|
||
|
|
}
|
||
|
|
</style>
|
||
|
|
|
||
|
|
<script>
|
||
|
|
// Helper function to get selected cleanup categories
|
||
|
|
function getSelectedCategories() {
|
||
|
|
const checkboxes = document.querySelectorAll('.cleanup-category:checked');
|
||
|
|
return Array.from(checkboxes).map(cb => cb.value);
|
||
|
|
}
|
||
|
|
|
||
|
|
// Show desktop warning if not in Tauri
|
||
|
|
if (typeof window.__TAURI__ === 'undefined') {
|
||
|
|
const warning = document.getElementById('desktop-warning');
|
||
|
|
if (warning) {
|
||
|
|
warning.style.display = 'flex';
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
// HTMX event handlers
|
||
|
|
document.body.addEventListener('htmx:afterSwap', function(evt) {
|
||
|
|
// Handle successful responses
|
||
|
|
if (evt.detail.successful) {
|
||
|
|
showNotification('Operation completed successfully', 'success');
|
||
|
|
}
|
||
|
|
});
|
||
|
|
|
||
|
|
document.body.addEventListener('htmx:responseError', function(evt) {
|
||
|
|
showNotification('Operation failed: ' + evt.detail.error, 'error');
|
||
|
|
});
|
||
|
|
|
||
|
|
// Show notification
|
||
|
|
function showNotification(message, type = 'success') {
|
||
|
|
const notification = document.getElementById('tools-notification');
|
||
|
|
if (notification) {
|
||
|
|
notification.textContent = message;
|
||
|
|
notification.className = `notification ${type} show`;
|
||
|
|
setTimeout(() => {
|
||
|
|
notification.classList.remove('show');
|
||
|
|
}, 3000);
|
||
|
|
}
|
||
|
|
}
|
||
|
|
</script>
|