Servis: radni nalog za servisera, hover napomena, responsive popravke

- Nalepnica: uklonjen QR (ostaje na uređaju u servisu, klijent nema šta da skenira);
oslobođen prostor iskorišćen za telefon klijenta i datume (prijem + rok)
- Radni nalog: obrisani „servis_stampa" i „servis_predracun"; nov interni
„servis_radni_nalog" (ruta /servis/{id}/radni-nalog) sa podacima samo za
servisera, bez cena, sa barkodom i praznim poljima (dijagnoza, urađen rad, potpis)
- Forma „Izmeni nalog": kartice „Serviser" i „Avans i napomena" spojene u jednu
„Serviser, avans i napomena"
- Servis kanban: dugme uz SN broj otvara internu napomenu (hover na desktopu,
tap→focus na mobilnom); okidač na omotaču da napomena ne treperi
- Detalji naloga (responsive): forme „Dodaj rad/deo" izvučene iz inline grid-a u
klase + @media (2 kolone na telefonu); tabele radova/delova u tabela-skrol
This commit is contained in:
2026-06-23 11:08:58 +02:00
parent 8e06b9cd97
commit 6a96d07156
10 changed files with 226 additions and 594 deletions
@@ -0,0 +1,217 @@
<!DOCTYPE html>
<html lang="sr">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Radni nalog {{.Nalog.BrojNaloga}}</title>
<style>
* { box-sizing: border-box; margin: 0; padding: 0; }
body { font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Arial, sans-serif; font-size: 13px; color: #111; background: #fff; }
.strana { max-width: 780px; margin: 0 auto; padding: 32px 40px; }
/* zaglavlje */
.zaglavlje { display: flex; justify-content: space-between; align-items: flex-start; margin-bottom: 24px; padding-bottom: 14px; border-bottom: 2px solid #111; gap: 20px; }
.firma-naziv { font-size: 16px; font-weight: 700; }
.firma-podnaslov { font-size: 11px; color: #666; text-transform: uppercase; letter-spacing: 1px; margin-top: 2px; }
.nalog-desno { text-align: right; }
.nalog-naslov { font-size: 11px; color: #555; text-transform: uppercase; letter-spacing: 0.6px; margin-bottom: 2px; }
.nalog-broj { font-size: 22px; font-weight: 700; font-family: monospace; }
.status { display: inline-block; margin-top: 6px; padding: 2px 10px; border-radius: 20px; font-size: 11px; font-weight: 600; border: 1.5px solid #111; }
.barkod { margin-top: 8px; }
.barkod img { display: block; height: 11mm; width: 52mm; object-fit: fill; margin-left: auto; }
/* odeljci */
.odeljak { margin-bottom: 18px; }
.odeljak-naslov { font-size: 11px; font-weight: 600; text-transform: uppercase; letter-spacing: 0.8px; color: #555; margin-bottom: 8px; padding-bottom: 4px; border-bottom: 0.5px solid #ccc; }
/* grid sa podacima */
.podaci-grid { display: grid; grid-template-columns: repeat(3, 1fr); gap: 14px; }
.podaci-grid-2 { display: grid; grid-template-columns: 1fr 1fr; gap: 14px; }
.polje-labela { font-size: 10px; color: #777; text-transform: uppercase; letter-spacing: 0.4px; margin-bottom: 3px; }
.polje-vrednost { font-size: 13px; font-weight: 500; }
.polje-vrednost-mono { font-family: monospace; font-size: 14px; font-weight: 600; }
.polje-tekst { font-size: 13px; line-height: 1.6; white-space: pre-wrap; }
.prazno { color: #aaa; font-style: italic; }
/* istaknut PIN/lozinka — serviseru treba pristup */
.pin-blok { display: inline-block; padding: 4px 12px; background: #fef9c3; border: 1px solid #facc15; border-radius: 6px; }
/* tabela delova bez cena */
.tabela { width: 100%; border-collapse: collapse; margin-top: 6px; }
.tabela th { font-size: 11px; font-weight: 600; text-transform: uppercase; letter-spacing: 0.4px; color: #555; padding: 6px 8px; border-bottom: 1.5px solid #111; text-align: left; }
.tabela th.desno { text-align: right; }
.tabela td { padding: 7px 8px; border-bottom: 0.5px solid #ddd; font-size: 13px; }
.tabela td.desno { text-align: right; }
/* prazni okviri za rukom upisivanje */
.upis-okvir { border: 0.5px solid #bbb; border-radius: 6px; padding: 10px 12px; min-height: 70px; background:
repeating-linear-gradient(to bottom, transparent, transparent 27px, #eee 27px, #eee 28px); }
.upis-veliki { min-height: 110px; }
.upis-labela { font-size: 10px; color: #777; text-transform: uppercase; letter-spacing: 0.4px; margin-bottom: 6px; }
/* zavrsetak — vreme i potpis */
.zavrsetak { display: grid; grid-template-columns: 1fr 1fr; gap: 40px; margin-top: 28px; padding-top: 16px; border-top: 0.5px solid #ccc; }
.linija { border-top: 1px solid #888; margin-top: 40px; padding-top: 6px; font-size: 11px; color: #555; }
@media print {
body { font-size: 12px; }
.strana { padding: 16px 20px; max-width: 100%; }
.dugme-stampa { display: none !important; }
@page { size: A4; margin: 12mm 14mm; }
}
.dugme-stampa { position: fixed; bottom: 24px; right: 24px; background: #111; color: #fff; border: none; padding: 12px 22px; border-radius: 8px; font-size: 14px; font-weight: 500; cursor: pointer; box-shadow: 0 4px 12px rgba(0,0,0,0.2); }
.dugme-stampa:hover { background: #333; }
</style>
</head>
<body>
<div class="strana">
<!-- zaglavlje -->
<div class="zaglavlje">
<div>
<div class="firma-naziv">{{if .NazivFirme}}{{.NazivFirme}}{{else}}— naziv firme —{{end}}</div>
<div class="firma-podnaslov">Radni nalog — interni</div>
</div>
<div class="nalog-desno">
<div class="nalog-naslov">Broj naloga</div>
<div class="nalog-broj">{{.Nalog.BrojNaloga}}</div>
<div><span class="status">{{.Nalog.Status}}</span></div>
{{if .Barkod}}
<div class="barkod"><img src="data:image/png;base64,{{.Barkod}}" alt="Barkod {{.Nalog.BrojNaloga}}"></div>
{{end}}
</div>
</div>
<!-- osnovni podaci -->
<div class="odeljak">
<div class="odeljak-naslov">Osnovni podaci</div>
<div class="podaci-grid">
<div>
<div class="polje-labela">Datum prijema</div>
<div class="polje-vrednost">{{.Nalog.DatumPrijema.Format "02.01.2006. u 15:04"}}</div>
</div>
{{if .Nalog.PredvidjenDatum}}
<div>
<div class="polje-labela">Predviđen rok</div>
<div class="polje-vrednost">{{.Nalog.PredvidjenDatum.Format "02.01.2006."}}</div>
</div>
{{end}}
{{if .TehnicarNaziv}}
<div>
<div class="polje-labela">Serviser</div>
<div class="polje-vrednost">{{.TehnicarNaziv}}</div>
</div>
{{end}}
<div>
<div class="polje-labela">Klijent</div>
<div class="polje-vrednost">{{if .KlijentNaziv}}{{.KlijentNaziv}}{{else}}<span class="prazno"></span>{{end}}</div>
</div>
{{if .KlijentTelefon}}
<div>
<div class="polje-labela">Telefon klijenta</div>
<div class="polje-vrednost">{{telefon .KlijentTelefon}}</div>
</div>
{{end}}
</div>
</div>
<!-- uređaj -->
<div class="odeljak">
<div class="odeljak-naslov">Uređaj</div>
<div class="podaci-grid" style="margin-bottom:12px;">
<div>
<div class="polje-labela">Naziv uređaja</div>
<div class="polje-vrednost">{{.Nalog.Uredjaj}}</div>
</div>
<div>
<div class="polje-labela">Serijski broj</div>
<div class="polje-vrednost-mono">{{if .Nalog.SerijskiBroj}}{{.Nalog.SerijskiBroj}}{{else}}<span class="prazno"></span>{{end}}</div>
</div>
{{if .Nalog.PinUredjaja}}
<div>
<div class="polje-labela">PIN / lozinka</div>
<div class="pin-blok polje-vrednost-mono">{{.Nalog.PinUredjaja}}</div>
</div>
{{end}}
</div>
<div style="margin-bottom:10px;">
<div class="polje-labela">Prijavljen kvar</div>
<div class="polje-tekst">{{if .Nalog.OpisKvara}}{{.Nalog.OpisKvara}}{{else}}<span class="prazno"></span>{{end}}</div>
</div>
{{if .Nalog.TrazeneNadogradnje}}
<div style="margin-bottom:10px;">
<div class="polje-labela">Tražene nadogradnje</div>
<div class="polje-tekst">{{.Nalog.TrazeneNadogradnje}}</div>
</div>
{{end}}
{{if or .Nalog.Ostecenja .Nalog.Pribor}}
<div class="podaci-grid-2">
{{if .Nalog.Ostecenja}}
<div>
<div class="polje-labela">Oštećenja pri prijemu</div>
<div class="polje-tekst">{{.Nalog.Ostecenja}}</div>
</div>
{{end}}
{{if .Nalog.Pribor}}
<div>
<div class="polje-labela">Pribor i oprema</div>
<div class="polje-tekst">{{.Nalog.Pribor}}</div>
</div>
{{end}}
</div>
{{end}}
</div>
<!-- rezervisani/ugrađeni delovi — bez cena -->
{{if .ServisniDelovi}}
<div class="odeljak">
<div class="odeljak-naslov">Delovi na nalogu</div>
<table class="tabela">
<thead>
<tr>
<th>Artikal</th>
<th class="desno" style="width:90px;">Količina</th>
</tr>
</thead>
<tbody>
{{range .ServisniDelovi}}
<tr>
<td>{{.ArtikalNaziv}}</td>
<td class="desno">{{.Kolicina}}</td>
</tr>
{{end}}
</tbody>
</table>
</div>
{{end}}
<!-- prazna polja za servisera -->
<div class="odeljak">
<div class="upis-labela">Dijagnoza / utvrđen kvar</div>
<div class="upis-okvir upis-veliki"></div>
</div>
<div class="odeljak">
<div class="upis-labela">Urađen rad</div>
<div class="upis-okvir upis-veliki"></div>
</div>
<!-- vreme i potpis -->
<div class="zavrsetak">
<div>
<div class="polje-labela">Datum završetka / utrošeno vreme</div>
<div class="linija">&nbsp;</div>
</div>
<div>
<div class="polje-labela">Potpis servisera</div>
<div class="linija">&nbsp;</div>
</div>
</div>
</div>
<button class="dugme-stampa" onclick="window.print()">Štampaj</button>
</body>
</html>