Remove refresh icon and fix Safari/WebKit runtime errors

- Removed manual refresh button from frontend (kept auto-refresh functionality)
- Fixed WebKit 'object cannot be found' error by replacing absolute positioning with flexbox
- Added lazy loading to images to prevent preload warnings
- Cleaned up unused imports and variables:
  - Removed unused useRef import
  - Removed unused colors state variable and colorService
  - Removed unused ColorSwatch import from FilamentTableV2
  - Removed unused getModifierIcon function from MaterialBadge
- Updated tests to match current implementation
- Improved layout stability for better cross-browser compatibility
- Removed temporary migration scripts

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
DaX
2025-06-30 22:37:30 +02:00
parent 58b3ff2dec
commit 12e91d4c3e
33 changed files with 1646 additions and 668 deletions

View File

@@ -1,6 +1,6 @@
'use client'
import { useState, useEffect, useRef } from 'react';
import { useState, useEffect } from 'react';
import { FilamentTableV2 } from '../src/components/FilamentTableV2';
import { Filament } from '../src/types/filament';
import { filamentService } from '../src/services/api';
@@ -40,8 +40,8 @@ export default function Home() {
setLoading(true);
setError(null);
const filaments = await filamentService.getAll();
setFilaments(filaments);
const filamentsData = await filamentService.getAll();
setFilaments(filamentsData);
} catch (err: any) {
console.error('API Error:', err);
@@ -62,6 +62,22 @@ export default function Home() {
useEffect(() => {
fetchFilaments();
// Auto-refresh data every 30 seconds to stay in sync
const interval = setInterval(() => {
fetchFilaments();
}, 30000);
// Also refresh when window regains focus
const handleFocus = () => {
fetchFilaments();
};
window.addEventListener('focus', handleFocus);
return () => {
clearInterval(interval);
window.removeEventListener('focus', handleFocus);
};
}, []);
const handleLogoClick = () => {
@@ -73,36 +89,28 @@ export default function Home() {
<div className="min-h-screen bg-gray-50 dark:bg-gray-900 transition-colors">
<header className="bg-gradient-to-r from-blue-50 to-orange-50 dark:from-gray-800 dark:to-gray-900 shadow-lg transition-all duration-300">
<div className="max-w-7xl mx-auto px-4 sm:px-6 lg:px-8 py-4">
<div className="flex flex-col sm:flex-row justify-between items-center gap-4">
<button
onClick={handleLogoClick}
className="group hover:scale-105 transition-transform duration-200"
title="Klikni za reset"
>
<h1 className="text-3xl font-bold bg-gradient-to-r from-blue-600 to-orange-600 dark:from-blue-400 dark:to-orange-400 bg-clip-text text-transparent group-hover:from-blue-700 group-hover:to-orange-700 dark:group-hover:from-blue-300 dark:group-hover:to-orange-300 transition-all">
Filamenteka
</h1>
</button>
<div className="flex items-center justify-between">
<div className="flex-1 flex justify-center gap-3 text-lg">
<span className="text-blue-700 dark:text-blue-300 font-medium animate-pulse whitespace-nowrap">
Kupovina po gramu dostupna
</span>
<span className="text-gray-400 dark:text-gray-600"></span>
<span className="text-orange-700 dark:text-orange-300 font-medium animate-pulse whitespace-nowrap">
Popust za 5+ komada
</span>
</div>
<div className="flex flex-col sm:flex-row items-center gap-3 text-sm">
<div className="flex flex-col sm:flex-row gap-3 text-center">
<span className="text-blue-700 dark:text-blue-300 font-medium animate-pulse whitespace-nowrap">
Kupovina po gramu dostupna
</span>
<span className="hidden sm:inline text-gray-400 dark:text-gray-600"></span>
<span className="text-orange-700 dark:text-orange-300 font-medium animate-pulse whitespace-nowrap">
Popust za 5+ komada
</span>
</div>
{mounted && (
<div className="flex-shrink-0 ml-4">
{mounted ? (
<button
onClick={() => setDarkMode(!darkMode)}
className="p-2 bg-white/50 dark:bg-gray-700/50 backdrop-blur text-gray-800 dark:text-gray-200 rounded-full hover:bg-white/80 dark:hover:bg-gray-600/80 transition-all duration-200 hover:scale-110 shadow-md ml-2"
className="p-2 bg-white/50 dark:bg-gray-700/50 backdrop-blur text-gray-800 dark:text-gray-200 rounded-full hover:bg-white/80 dark:hover:bg-gray-600/80 transition-all duration-200 shadow-md"
title={darkMode ? 'Svetla tema' : 'Tamna tema'}
>
{darkMode ? '☀️' : '🌙'}
</button>
) : (
<div className="w-10 h-10" />
)}
</div>
</div>
@@ -110,11 +118,31 @@ export default function Home() {
</header>
<main className="max-w-7xl mx-auto px-4 sm:px-6 lg:px-8 py-8">
{/* Logo centered above content */}
<div className="flex justify-center mb-8">
<button
onClick={handleLogoClick}
className="group transition-transform duration-200"
title="Klikni za reset"
>
{/* Using next/image would cause preload, so we use regular img with loading="lazy" */}
<img
src="/logo.png"
alt="Filamenteka"
loading="lazy"
decoding="async"
className="h-36 sm:h-44 md:h-52 w-auto drop-shadow-lg group-hover:drop-shadow-2xl transition-all duration-200"
onError={(e) => {
const target = e.currentTarget as HTMLImageElement;
target.style.display = 'none';
}}
/>
</button>
</div>
<FilamentTableV2
key={resetKey}
filaments={filaments}
loading={loading}
error={error || undefined}
/>
</main>