Enhance UI transitions and loading effects across Proxmox views
- Implemented page load animations using Alpine.js for smoother transitions in various views including firewall, help, index, network, overview, reinstall, server, statistics, storage, subdomain, and system. - Added opacity and translate effects to elements for improved visual feedback during loading. - Enhanced hover effects on cards and buttons for better user interaction. - Adjusted transition timings and delays for a more cohesive user experience.
This commit is contained in:
@@ -342,31 +342,42 @@
|
||||
@endphp
|
||||
|
||||
<!-- Resource Stats Grid -->
|
||||
<div class="grid grid-cols-1 md:grid-cols-3 gap-4 lg:gap-5" wire:loading.class="opacity-50" wire:target="checkStatus">
|
||||
@foreach($resourceAllocations as $resource)
|
||||
<div class="group bg-white dark:bg-gray-900 border border-gray-200 dark:border-gray-800 rounded-2xl shadow-sm hover:shadow-md hover:border-gray-300 dark:hover:border-gray-700 transition-all duration-200 p-4 lg:p-5">
|
||||
<div class="grid grid-cols-1 md:grid-cols-3 gap-4 lg:gap-5"
|
||||
wire:loading.class="opacity-50"
|
||||
wire:target="checkStatus"
|
||||
x-data="{ loaded: false }"
|
||||
x-init="setTimeout(() => loaded = true, 100)">
|
||||
@foreach($resourceAllocations as $index => $resource)
|
||||
<div class="group bg-white dark:bg-gray-900 border border-gray-200 dark:border-gray-800 rounded-2xl shadow-sm p-4 lg:p-5
|
||||
transition-all duration-300 ease-out
|
||||
hover:shadow-lg hover:border-gray-300 dark:hover:border-gray-700
|
||||
hover:-translate-y-0.5 hover:scale-[1.01]"
|
||||
:class="loaded ? 'opacity-100 translate-y-0' : 'opacity-0 translate-y-4'"
|
||||
:style="loaded ? 'transition-delay: {{ $index * 75 }}ms' : ''">
|
||||
<div class="flex items-start justify-between mb-4">
|
||||
<h3 class="text-xs font-bold text-gray-600 dark:text-gray-400 uppercase tracking-widest opacity-75">{{ $resource['label'] }}</h3>
|
||||
<h3 class="text-xs font-bold text-gray-600 dark:text-gray-400 uppercase tracking-widest opacity-75 group-hover:opacity-100 transition-opacity duration-200">{{ $resource['label'] }}</h3>
|
||||
@if(isset($resource['badge']))
|
||||
<span class="text-xs font-bold px-2.5 py-1 rounded-full {{ $resource['badge']['label'] === 'Healthy' ? 'bg-success/15 text-success opacity-90' : ($resource['badge']['label'] === 'Watchlist' ? 'bg-warning/15 text-warning opacity-90' : 'bg-error/15 text-error opacity-90') }}">
|
||||
<span class="text-xs font-bold px-2.5 py-1 rounded-full transition-transform duration-200 group-hover:scale-105 {{ $resource['badge']['label'] === 'Healthy' ? 'bg-success/15 text-success opacity-90' : ($resource['badge']['label'] === 'Watchlist' ? 'bg-warning/15 text-warning opacity-90' : 'bg-error/15 text-error opacity-90') }}">
|
||||
{{ $resource['badge']['label'] }}
|
||||
</span>
|
||||
@endif
|
||||
</div>
|
||||
<div class="mb-3">
|
||||
<div class="text-3xl font-bold text-gray-900 dark:text-white tracking-tight mb-1">{{ $resource['usage_summary'] }}</div>
|
||||
<p class="text-xs text-gray-600 dark:text-gray-400 opacity-75 font-medium">{{ $resource['entitlement_label'] }}</p>
|
||||
<div class="text-3xl font-bold text-gray-900 dark:text-white tracking-tight mb-1 transition-colors duration-200 group-hover:text-primary">{{ $resource['usage_summary'] }}</div>
|
||||
<p class="text-xs text-gray-600 dark:text-gray-400 opacity-75 font-medium group-hover:opacity-90 transition-opacity duration-200">{{ $resource['entitlement_label'] }}</p>
|
||||
</div>
|
||||
@if($resource['used_percent'] !== null)
|
||||
<div class="space-y-2">
|
||||
<div class="relative w-full h-2.5 bg-gray-200 dark:bg-gray-700 rounded-full overflow-hidden shadow-inner">
|
||||
<div class="absolute inset-y-0 left-0 rounded-full transition-all duration-500 ease-out"
|
||||
style="width: {{ min(100, $resource['used_percent']) }}%; background: {{ $resource['gradient'] }}; box-shadow: 0 0 20px {{ $resource['gradient'] }};"></div>
|
||||
<div class="absolute inset-y-0 left-0 rounded-full transition-all duration-700 ease-out origin-left"
|
||||
x-data="{ width: 0 }"
|
||||
x-init="setTimeout(() => width = {{ min(100, $resource['used_percent']) }}, 300)"
|
||||
:style="'width: ' + width + '%; background: {{ $resource['gradient'] }}; box-shadow: 0 0 20px {{ $resource['gradient'] }};'"></div>
|
||||
</div>
|
||||
<div class="flex items-center justify-between">
|
||||
<span class="text-xs font-semibold text-gray-700 dark:text-gray-300">{{ number_format($resource['used_percent'], 1) }}%</span>
|
||||
<span class="text-xs font-semibold text-gray-700 dark:text-gray-300 group-hover:text-gray-900 dark:group-hover:text-white transition-colors duration-200">{{ number_format($resource['used_percent'], 1) }}%</span>
|
||||
@if($resource['used_percent'] > 100)
|
||||
<span class="text-xs font-bold text-error opacity-85">Over entitlement</span>
|
||||
<span class="text-xs font-bold text-error opacity-85 animate-pulse">Over entitlement</span>
|
||||
@endif
|
||||
</div>
|
||||
</div>
|
||||
@@ -376,26 +387,31 @@
|
||||
</div>
|
||||
|
||||
<!-- Main Grid Layout -->
|
||||
<div class="grid grid-cols-1 lg:grid-cols-2 gap-4 lg:gap-5">
|
||||
<div class="grid grid-cols-1 lg:grid-cols-2 gap-4 lg:gap-5"
|
||||
x-data="{ cardsLoaded: false }"
|
||||
x-init="setTimeout(() => cardsLoaded = true, 250)">
|
||||
<!-- Server Information Card -->
|
||||
<div class="bg-white dark:bg-gray-900 border border-gray-200 dark:border-gray-800 rounded-2xl shadow-sm hover:shadow-md hover:border-gray-300 dark:hover:border-gray-700 transition-all duration-200 overflow-hidden">
|
||||
<div class="flex items-center justify-between p-4 lg:p-5 bg-gradient-to-r from-primary/8 to-primary/4 border-b border-primary/20">
|
||||
<div class="bg-white dark:bg-gray-900 border border-gray-200 dark:border-gray-800 rounded-2xl shadow-sm overflow-hidden
|
||||
transition-all duration-300 ease-out
|
||||
hover:shadow-lg hover:border-gray-300 dark:hover:border-gray-700"
|
||||
:class="cardsLoaded ? 'opacity-100 translate-y-0' : 'opacity-0 translate-y-4'">
|
||||
<div class="flex items-center justify-between p-4 lg:p-5 bg-gradient-to-r from-primary/8 to-primary/4 border-b border-primary/20 transition-all duration-200 hover:from-primary/12 hover:to-primary/6">
|
||||
<div class="flex items-center gap-2.5">
|
||||
<svg class="size-5 text-primary opacity-80" fill="currentColor" viewBox="0 0 24 24"><rect x="2" y="3" width="20" height="5" rx="1" fill="currentColor"/><rect x="2" y="10" width="20" height="5" rx="1" fill="currentColor"/><circle cx="6" cy="5.5" r="0.7" fill="white" opacity="0.8"/><circle cx="6" cy="12.5" r="0.7" fill="white" opacity="0.8"/></svg>
|
||||
<svg class="size-5 text-primary opacity-80 transition-transform duration-200 hover:scale-110" fill="currentColor" viewBox="0 0 24 24"><rect x="2" y="3" width="20" height="5" rx="1" fill="currentColor"/><rect x="2" y="10" width="20" height="5" rx="1" fill="currentColor"/><circle cx="6" cy="5.5" r="0.7" fill="white" opacity="0.8"/><circle cx="6" cy="12.5" r="0.7" fill="white" opacity="0.8"/></svg>
|
||||
<h3 class="text-base sm:text-lg font-bold text-gray-900 dark:text-white">Server Information</h3>
|
||||
</div>
|
||||
</div>
|
||||
<div class="p-4 lg:p-5">
|
||||
<div class="space-y-3.5">
|
||||
<!-- Status -->
|
||||
<div class="flex items-center justify-between py-2.5 px-3 rounded-lg hover:bg-gray-50 dark:hover:bg-gray-800 transition-colors">
|
||||
<div class="flex items-center gap-2 text-sm font-semibold text-gray-600 dark:text-gray-400 opacity-80">
|
||||
<svg class="size-4 opacity-75" fill="none" stroke="currentColor" viewBox="0 0 24 24" stroke-width="2"><path d="M1 12s4-8 11-8 11 8 11 8-4 8-11 8-11-8-11-8z" stroke-linecap="round" stroke-linejoin="round"/><circle cx="12" cy="12" r="3" stroke-linecap="round" stroke-linejoin="round"/></svg>
|
||||
<div class="flex items-center justify-between py-2.5 px-3 rounded-lg hover:bg-gray-50 dark:hover:bg-gray-800 transition-all duration-200 hover:translate-x-0.5 group">
|
||||
<div class="flex items-center gap-2 text-sm font-semibold text-gray-600 dark:text-gray-400 opacity-80 group-hover:opacity-100 transition-opacity duration-200">
|
||||
<svg class="size-4 opacity-75 group-hover:opacity-100 transition-all duration-200 group-hover:scale-110" fill="none" stroke="currentColor" viewBox="0 0 24 24" stroke-width="2"><path d="M1 12s4-8 11-8 11 8 11 8-4 8-11 8-11-8-11-8z" stroke-linecap="round" stroke-linejoin="round"/><circle cx="12" cy="12" r="3" stroke-linecap="round" stroke-linejoin="round"/></svg>
|
||||
<span>Status</span>
|
||||
</div>
|
||||
<div>
|
||||
@if ($status && $status->status === 'running')
|
||||
<span class="inline-flex items-center gap-1.5 px-3 py-1.5 text-xs font-semibold bg-success/15 text-success rounded-full opacity-90">
|
||||
<span class="inline-flex items-center gap-1.5 px-3 py-1.5 text-xs font-semibold bg-success/15 text-success rounded-full opacity-90 transition-all duration-200 hover:opacity-100 hover:bg-success/20">
|
||||
<span class="w-1.5 h-1.5 bg-success rounded-full animate-pulse"></span>
|
||||
Running
|
||||
</span>
|
||||
@@ -408,22 +424,22 @@
|
||||
</div>
|
||||
</div>
|
||||
<!-- Operating System -->
|
||||
<div class="flex items-center justify-between py-2.5 px-3 rounded-lg hover:bg-gray-50 dark:hover:bg-gray-800 transition-colors">
|
||||
<div class="flex items-center gap-2 text-sm font-semibold text-gray-600 dark:text-gray-400 opacity-80">
|
||||
<svg class="size-4 opacity-75" fill="currentColor" viewBox="0 0 24 24"><circle cx="12" cy="12" r="10" fill="none" stroke="currentColor" stroke-width="2"/><circle cx="12" cy="4" r="1.5" fill="currentColor"/><circle cx="18" cy="15" r="1.5" fill="currentColor"/><circle cx="6" cy="15" r="1.5" fill="currentColor"/></svg>
|
||||
<div class="flex items-center justify-between py-2.5 px-3 rounded-lg hover:bg-gray-50 dark:hover:bg-gray-800 transition-all duration-200 hover:translate-x-0.5 group">
|
||||
<div class="flex items-center gap-2 text-sm font-semibold text-gray-600 dark:text-gray-400 opacity-80 group-hover:opacity-100 transition-opacity duration-200">
|
||||
<svg class="size-4 opacity-75 group-hover:opacity-100 transition-all duration-200 group-hover:scale-110" fill="currentColor" viewBox="0 0 24 24"><circle cx="12" cy="12" r="10" fill="none" stroke="currentColor" stroke-width="2"/><circle cx="12" cy="4" r="1.5" fill="currentColor"/><circle cx="18" cy="15" r="1.5" fill="currentColor"/><circle cx="6" cy="15" r="1.5" fill="currentColor"/></svg>
|
||||
<span>Operating System</span>
|
||||
</div>
|
||||
<span class="text-sm text-gray-900 dark:text-white font-medium opacity-90">{{ $server->os->name }}</span>
|
||||
<span class="text-sm text-gray-900 dark:text-white font-medium opacity-90 group-hover:opacity-100 transition-opacity duration-200">{{ $server->os->name }}</span>
|
||||
</div>
|
||||
<!-- Hostname -->
|
||||
<div class="flex items-center justify-between py-2.5 px-3 rounded-lg hover:bg-gray-50 dark:hover:bg-gray-800 transition-colors" x-data="{ showHostnameEditModal: @entangle('isEditingHostname') }">
|
||||
<div class="flex items-center gap-2 text-sm font-semibold text-gray-600 dark:text-gray-400 opacity-80">
|
||||
<svg class="size-4 opacity-75" fill="none" stroke="currentColor" viewBox="0 0 24 24" stroke-width="2"><rect x="2" y="3" width="20" height="14" rx="2" stroke-linecap="round" stroke-linejoin="round"/><path d="M8 21h8M12 17v4" stroke-linecap="round" stroke-linejoin="round"/></svg>
|
||||
<div class="flex items-center justify-between py-2.5 px-3 rounded-lg hover:bg-gray-50 dark:hover:bg-gray-800 transition-all duration-200 hover:translate-x-0.5 group" x-data="{ showHostnameEditModal: @entangle('isEditingHostname') }">
|
||||
<div class="flex items-center gap-2 text-sm font-semibold text-gray-600 dark:text-gray-400 opacity-80 group-hover:opacity-100 transition-opacity duration-200">
|
||||
<svg class="size-4 opacity-75 group-hover:opacity-100 transition-all duration-200 group-hover:scale-110" fill="none" stroke="currentColor" viewBox="0 0 24 24" stroke-width="2"><rect x="2" y="3" width="20" height="14" rx="2" stroke-linecap="round" stroke-linejoin="round"/><path d="M8 21h8M12 17v4" stroke-linecap="round" stroke-linejoin="round"/></svg>
|
||||
<span>Hostname</span>
|
||||
</div>
|
||||
<div class="flex items-center gap-2">
|
||||
<code class="text-sm text-gray-900 dark:text-white font-mono opacity-90">{{ $server->hostname ?? $status->name ?? 'N/A' }}</code>
|
||||
<button wire:click="startEditingHostname" type="button" class="text-primary opacity-70 hover:opacity-100 transition-opacity">
|
||||
<code class="text-sm text-gray-900 dark:text-white font-mono opacity-90 group-hover:opacity-100 transition-opacity duration-200">{{ $server->hostname ?? $status->name ?? 'N/A' }}</code>
|
||||
<button wire:click="startEditingHostname" type="button" class="text-primary opacity-70 hover:opacity-100 transition-all duration-200 hover:scale-110">
|
||||
<x-ri-edit-line class="size-4" />
|
||||
</button>
|
||||
</div>
|
||||
|
||||
Reference in New Issue
Block a user