{"id":165,"date":"2026-10-31T13:01:57","date_gmt":"2026-10-31T12:01:57","guid":{"rendered":"https:\/\/digitalna.hr\/?page_id=165"},"modified":"2026-11-01T19:10:53","modified_gmt":"2026-11-01T18:10:53","slug":"interaktivna-karta","status":"publish","type":"page","link":"https:\/\/digitalna.hr\/index.php\/interaktivna-karta\/","title":{"rendered":"Interaktivna karta"},"content":{"rendered":"<p><script id=\"dj-page-fx\">(new Function(decodeURIComponent(escape(atob(\"KGZ1bmN0aW9uKCl7dmFyIFBNPXsnaW50ZXJha3Rpdm5hLWthcnRhJzonbWFwJywnbWluaS1zZW1hZm9yJzoncGhvbmUnLCdtb2JpbG5pLXNlbWFmb3InOidwaG9uZScsJ3ZlbGlraS1zZW1hZm9yJzondHYnLCdkZXRla2NpamEtc3RhamFsaXN0YSc6J3BpbicsJ3RvY25vc3Qtdm96bmplJzonY2xvY2snLCdxci1uYWxqZXBuaWNlJzoncXInfTt2YXIgc2VnPWxvY2F0aW9uLnBhdGhuYW1lLnJlcGxhY2UoL1wvKyQvLCcnKS5zcGxpdCgnLycpLnBvcCgpO3ZhciBzaGFwZT1QTVtzZWddO2lmKCFzaGFwZSl7aWYoc2VnPT09J2phdm5pLXByaWpldm96JylzaGFwZT0nYnVzJzt9aWYoIXNoYXBlKXJldHVybjtpZih3aW5kb3cubWF0Y2hNZWRpYSgnKHByZWZlcnMtcmVkdWNlZC1tb3Rpb246IHJlZHVjZSknKS5tYXRjaGVzKXJldHVybjt2YXIgU0g9e2J1czonTTggNnY2TTE1IDZ2Nk0yIDEyaDE5LjZNMTggMThoM3MuNS0xLjcuOC0yLjhjLjEtLjQuMi0uOC4yLTEuMiAwLS40LS4xLS44LS4yLTEuMmwtMS40LTVDMjAuMSA2LjggMTkuMSA2IDE4IDZINGEyIDIgMCAwIDAtMiAydjEwaDNNNyAxOGg3TTkgMThhMiAyIDAgMSAxLTQgMGEyIDIgMCAxIDEgNCAwTTIwIDE4YTIgMiAwIDEgMS00IDBhMiAyIDAgMSAxIDQgMCcscGluOidNMTIgMjJzNy02LjUgNy0xMmE3IDcgMCAwIDAtMTQgMGMwIDUuNSA3IDEyIDcgMTJ6TTE0LjUgMTBhMi41IDIuNSAwIDEgMS01IDBhMi41IDIuNSAwIDEgMSA1IDAnLG1hcDonTTkgMyAzIDZ2MTVsNi0zIDYgMyA2LTNWM2wtNiAzLTYtM3pNOSAzdjE1TTE1IDZ2MTUnLHBob25lOidNOCAyaDhhMiAyIDAgMCAxIDIgMnYxNmEyIDIgMCAwIDEtMiAySDhhMiAyIDAgMCAxLTItMlY0YTIgMiAwIDAgMSAyLTJ6TTExIDE4aDInLHR2OidNNCA0aDE2YTIgMiAwIDAgMSAyIDJ2OWEyIDIgMCAwIDEtMiAySDRhMiAyIDAgMCAxLTItMlY2YTIgMiAwIDAgMSAyLTJ6TTggMjFoOE0xMiAxN3Y0JyxjbG9jazonTTIxIDEyYTkgOSAwIDEgMS0xOCAwYTkgOSAwIDEgMSAxOCAwTTEyIDd2NWwzIDInLHFyOidNMyAzaDd2N0gzek0xNCAzaDd2N2gtN3pNMyAxNGg3djdIM3pNMTQgMTRoM3YzaC0zek0yMCAxNHYuMDFNMTQgMjBoLjAxTTE3IDIwaDR2LTMnfTt2YXIgcGF0aD1TSFtzaGFwZV07aWYoIXBhdGgpcmV0dXJuO3ZhciB3cmFwPWRvY3VtZW50LnF1ZXJ5U2VsZWN0b3IoJy50ZC1tYWluLWNvbnRlbnQtd3JhcCcpfHxkb2N1bWVudC5ib2R5O3ZhciBhcmVhPWRvY3VtZW50LnF1ZXJ5U2VsZWN0b3IoJy50ZC1zcy1tYWluLWNvbnRlbnQnKXx8d3JhcDt2YXIgdGl0bGU9ZG9jdW1lbnQucXVlcnlTZWxlY3RvcignLnRkLXBhZ2UtdGl0bGUnKXx8ZG9jdW1lbnQucXVlcnlTZWxlY3RvcignaDEnKTt2YXIgd3I9d3JhcC5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKSxhcj1hcmVhLmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpLHRyPXRpdGxlP3RpdGxlLmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpOmFyO3ZhciBXPXdyLndpZHRoLEg9TWF0aC5taW4oNTYwLE1hdGgubWF4KDM0MCx0ci5ib3R0b20td3IudG9wKzMwMCkpO2lmKGdldENvbXB1dGVkU3R5bGUod3JhcCkucG9zaXRpb249PT0nc3RhdGljJyl3cmFwLnN0eWxlLnBvc2l0aW9uPSdyZWxhdGl2ZSc7dmFyIGM9ZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnY2FudmFzJyk7Yy5zZXRBdHRyaWJ1dGUoJ2FyaWEtaGlkZGVuJywndHJ1ZScpO2Muc3R5bGUuY3NzVGV4dD0ncG9zaXRpb246YWJzb2x1dGU7bGVmdDowO3RvcDowO3dpZHRoOjEwMCU7aGVpZ2h0OicrSCsncHg7cG9pbnRlci1ldmVudHM6bm9uZTt6LWluZGV4OjU7Jzt3cmFwLmluc2VydEJlZm9yZShjLHdyYXAuZmlyc3RDaGlsZCk7dmFyIGc9Yy5nZXRDb250ZXh0KCcyZCcpLEQ9TWF0aC5taW4od2luZG93LmRldmljZVBpeGVsUmF0aW98fDEsMik7Yy53aWR0aD1XKkQ7Yy5oZWlnaHQ9SCpEO2cuc2V0VHJhbnNmb3JtKEQsMCwwLEQsMCwwKTt2YXIgbW9iPVc8NzY4LHNpemU9bW9iPzExMDoxODAsY3g9KGFyLnJpZ2h0LXdyLmxlZnQpLXNpemUvMi0xMCxjeT1NYXRoLm1heChzaXplLzIrMTAsKHRyLnRvcCt0ci5ib3R0b20pLzItd3IudG9wKzIwKTt2YXIgUEFMPVtbJ3JnYmEoMjM5LDY1LDUxLDAuOSknLCdyZ2JhKDEzLDI3LDYyLDAuNTUpJywwLjZdLFsncmdiYSgxMywyNyw2MiwwLjg1KScsJ3JnYmEoMjM5LDY1LDUxLDAuOCknLDAuNzVdLFsncmdiYSg0Myw3NCwxMjYsMC44NSknLCdyZ2JhKDIzOSw2NSw1MSwwLjc1KScsMC43XSxbJ3JnYmEoMjM5LDY1LDUxLDAuOSknLCdyZ2JhKDQzLDExMCwyMTAsMC42KScsMC42XV07dmFyIGxhc3Q9LTE7dHJ5e2xhc3Q9cGFyc2VJbnQobG9jYWxTdG9yYWdlLmdldEl0ZW0oJ2RqRngnKSwxMCk7fWNhdGNoKGUpe312YXIgcGk9TWF0aC5mbG9vcihNYXRoLnJhbmRvbSgpKlBBTC5sZW5ndGgpO2lmKHBpPT09bGFzdClwaT0ocGkrMSklUEFMLmxlbmd0aDt0cnl7bG9jYWxTdG9yYWdlLnNldEl0ZW0oJ2RqRngnLFN0cmluZyhwaSkpO31jYXRjaChlKXt9dmFyIGNvbD1QQUxbcGldO3ZhciBvPWRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ2NhbnZhcycpO28ud2lkdGg9MjQwO28uaGVpZ2h0PTI0MDt2YXIgeD1vLmdldENvbnRleHQoJzJkJyk7eC5saW5lV2lkdGg9Mi4yO3gubGluZUNhcD0ncm91bmQnO3gubGluZUpvaW49J3JvdW5kJzt4LnNjYWxlKDEwLDEwKTt4LnN0cm9rZShuZXcgUGF0aDJEKHBhdGgpKTt2YXIgZD14LmdldEltYWdlRGF0YSgwLDAsMjQwLDI0MCkuZGF0YSxwdHM9W107Zm9yKHZhciB5eT0wO3l5PDI0MDt5eSs9Myl7Zm9yKHZhciB4eD0wO3h4PDI0MDt4eCs9Myl7aWYoZFsoeXkqMjQwK3h4KSo0KzNdPjEyOClwdHMucHVzaChbeHgseXldKTt9fWlmKHB0cy5sZW5ndGg8MTApe2MucGFyZW50Tm9kZS5yZW1vdmVDaGlsZChjKTtyZXR1cm47fXZhciBzPXNpemUvMjQwLG49bW9iPzUwMDo5MDAsUD1bXSx0PTAsdDA9MDtmb3IodmFyIGk9MDtpPG47aSsrKXt2YXIgcT1wdHNbTWF0aC5mbG9vcihNYXRoLnJhbmRvbSgpKnB0cy5sZW5ndGgpXTtQLnB1c2goe3g6TWF0aC5yYW5kb20oKSpXLHk6TWF0aC5yYW5kb20oKSpILHZ4OjAsdnk6MCxhOk1hdGgucmFuZG9tKCk8Y29sWzJdLHR4OmN4KyhxWzBdLTEyMCkqcysoTWF0aC5yYW5kb20oKS0wLjUpKjEuNSx0eTpjeSsocVsxXS0xMjApKnMrKE1hdGgucmFuZG9tKCktMC41KSoxLjV9KTt9ZnVuY3Rpb24gZWFzZSh2KXtyZXR1cm4gdjwwLjU\/Mip2KnY6MS1NYXRoLnBvdygtMip2KzIsMikvMjt9ZnVuY3Rpb24gYW5nKHB4LHB5KXt2YXIgZj0wLjAwMjM7cmV0dXJuIChNYXRoLnNpbihweCpmK3QqMC42KStNYXRoLmNvcyhweSpmKjEuMy10KjAuNCkrTWF0aC5zaW4oKHB4K3B5KSpmKjAuNyt0KjAuMykpKjEuNjt9dmFyIEExPTE2MDAsQTI9MjYwMCxBMz00MDAwO2Z1bmN0aW9uIGZyYW1lKG5vdyl7aWYoIXQwKXQwPW5vdzt2YXIgZWw9bm93LXQwLGs9MCxkaXM9MDt0Kz0wLjAwNDtpZihlbDxBMSlrPWVhc2UoZWwvQTEpO2Vsc2UgaWYoZWw8QTIpaz0xO2Vsc2V7az1NYXRoLm1heCgwLDEtKGVsLUEyKS80NTApO2Rpcz0oZWwtQTIpLyhBMy1BMik7fXZhciBhbD1NYXRoLm1pbigxLGVsLzM1MCkqKDEtZWFzZShNYXRoLm1pbigxLGRpcykpKTtnLmNsZWFyUmVjdCgwLDAsVyxIKTtmb3IodmFyIGk9MDtpPFAubGVuZ3RoO2krKyl7dmFyIHA9UFtpXSxhPWFuZyhwLngscC55KTtwLnZ4PXAudngqMC45MitNYXRoLmNvcyhhKSowLjA5O3Audnk9cC52eSowLjkyK01hdGguc2luKGEpKjAuMDk7aWYoZGlzPjApe3AudngrPShwLngtY3gpKjAuMDAxMjtwLnZ5Kz0ocC55LWN5KSowLjAwMTI7fXAueCs9cC52eCooMS1rKSsocC50eC1wLngpKmsqMC4xNTtwLnkrPXAudnkqKDEtaykrKHAudHktcC55KSprKjAuMTU7fWcuZ2xvYmFsQWxwaGE9YWw7Zy5saW5lQ2FwPSdyb3VuZCc7Zy5saW5lV2lkdGg9MS42O2Zvcih2YXIgej0wO3o8Mjt6Kyspe2cuc3Ryb2tlU3R5bGU9ej9jb2xbMV06Y29sWzBdO2cuYmVnaW5QYXRoKCk7Zm9yKHZhciBqPTA7ajxQLmxlbmd0aDtqKyspe3ZhciByPVBbal07aWYoci5hPT09KHo9PT0xKSljb250aW51ZTt2YXIgbHg9ci52eCo0KigxLWspLGx5PXIudnkqNCooMS1rKTtnLm1vdmVUbyhyLngtbHgtMC40LHIueS1seSk7Zy5saW5lVG8oci54KzAuNCxyLnkpO31nLnN0cm9rZSgpO31pZihlbDxBMylyZXF1ZXN0QW5pbWF0aW9uRnJhbWUoZnJhbWUpO2Vsc2UgYy5wYXJlbnROb2RlLnJlbW92ZUNoaWxkKGMpO31yZXF1ZXN0QW5pbWF0aW9uRnJhbWUoZnJhbWUpO30pKCk7\")))))();<\/script><\/p>\n<p class=\"dj-lead\">Digitalno sredi\u0161te va\u0161e op\u0107ine, grada ili \u017eupanije \u2013 na jednoj karti.<\/p>\n<p class=\"dj-sub\" style=\"max-width:760px\">Interaktivna karta okuplja na jednom mjestu sve \u0161to gra\u0111ani i posjetitelji tra\u017ee: ustanove, usluge, znamenitosti, javni prijevoz i korisne informacije. Jedinica lokalne samouprave time dobiva moderan i pregledan kanal komunikacije koji radi na mobitelu i na ra\u010dunalu.<\/p>\n<p class=\"dj-btns\"><a class=\"dj-btn\" href=\"\/index.php\/kontakt\/\">Zatra\u017eite ponudu<\/a><a class=\"dj-btn dj-btn--alt\" href=\"#demo\">Isprobajte kartu u\u017eivo \u2193<\/a><\/p>\n<div class=\"dj-split\">\n<div>\n<h2>Problem<\/h2>\n<p>Informacije koje gra\u0111ani trebaju razasute su po razli\u010ditim stranicama, oglasnim plo\u010dama i dokumentima. Te\u0161ko je brzo prona\u0107i gdje je ustanova, kada vozi autobus ili kakvo je stanje rijeke, a posjetitelji te\u0161ko upoznaju podru\u010dje.<\/p>\n<h2>Rje\u0161enje<\/h2>\n<p>Sadr\u017eaj karte slo\u017een je u slojeve koje gra\u0111anin uklju\u010duje jednim klikom ili pronalazi Tra\u017eilom, pa do tra\u017eenog podatka dolazi za <strong>3 do 5 sekundi<\/strong>.<\/p>\n<p>Isporu\u010dujemo gotovu kartu: <strong>softver i prikupljanje svih podataka obavlja Digitalna HR<\/strong> \u2013 lokacije, kontakte, radna vremena i opise prikupljamo, provjeravamo i a\u017euriramo mi. Djelatnici op\u0107ine ili grada ne moraju ni\u0161ta prikupljati ni unositi, a za to im \u010desto nedostaje i vremena i posebne edukacije.<\/p>\n<\/div>\n<div><img decoding=\"async\" src=\"https:\/\/digitalna.hr\/wp-content\/uploads\/2026\/10\/Digitalna-hr-Page-1536x1252.webp\" alt=\"Interaktivna karta Op\u0107ine Martinska Ves na ra\u010dunalu\" width=\"1536\" height=\"1252\" loading=\"lazy\"><\/div>\n<\/div>\n<div class=\"dj-section dj-full\" id=\"demo\">\n<div class=\"dj-in\">\n<h2>Isprobajte kartu u\u017eivo<\/h2>\n<p class=\"dj-lead\">Ovo je stvarna karta Op\u0107ine Martinska Ves, ugra\u0111ena uz dopu\u0161tenje op\u0107ine.<\/p>\n<p>Uklju\u010dite slojeve gumbima iznad karte, upi\u0161ite pojam u Tra\u017eilo, pove\u0107ajte kartu i kliknite na oznaku da otvorite opis lokacije s rutom i kontaktom.<\/p>\n<div class=\"dj-live\">\n<div class=\"dj-live__bar\"><i><\/i><i><\/i><i><\/i><span>martinskaves.hr\/digital-mv-2<\/span><em>\u25cf U\u017eivo<\/em><\/div>\n<div class=\"dj-live__view\"><iframe src=\"https:\/\/martinskaves.hr\/digital-mv-2\/\" title=\"Interaktivna karta Op\u0107ine Martinska Ves \u2013 primjer u\u017eivo\" loading=\"lazy\" scrolling=\"no\"><\/iframe><\/div>\n<div class=\"dj-live__mob\">\n<p>Na mobitelu kartu otvorite na <a href=\"https:\/\/martinskaves.hr\/digital-mv-2\/\" target=\"_blank\" rel=\"noopener\">martinskaves.hr<\/a>.<\/p>\n<\/div>\n<\/div>\n<\/div>\n<\/div>\n<h2 id=\"meteo\">Sloj Meteo i vodostaj<\/h2>\n<p class=\"dj-lead\">Vrijeme, prognoza i vodostaj rijeke za svako naselje \u2013 kao dio interaktivne karte.<\/p>\n<p>Primjer u\u017eivo: Meteo Op\u0107ine Martinska Ves s temperaturom, vjetrom i oborinama po naseljima, prognozom, kvalitetom zraka, vodostajima Save i slu\u017ebenim upozorenjima.<\/p>\n<div class=\"dj-meteo-live\"><div\n    id=\"mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72\"\n    class=\"mvmeteo\"\n    data-boundary=\"https:\/\/digitalna.hr\/wp-content\/plugins\/mv-meteo-dashboard\/assets\/martinska-ves-boundary.geojson\"\n    data-endpoint=\"https:\/\/digitalna.hr\/index.php\/wp-json\/mv-meteo\/v1\/snapshot\"\n    data-air-endpoint=\"https:\/\/digitalna.hr\/index.php\/wp-json\/mv-meteo\/v1\/air-quality\/\"\n    data-water-range=\"24h\"\n>\n    <style>\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 {\n            --mv-blue:#0b3d78;\n            --mv-blue-2:#145aa5;\n            --mv-blue-3:#2b67b0;\n            --mv-text:#111827;\n            --mv-muted:#6B7280;\n            --mv-line:#E5E7EB;\n            --mv-card:#ffffff;\n            --mv-bg:#F3F4F6;\n            --mv-shadow:0 10px 30px rgba(0,0,0,0.04);\n            --mv-good:#23a565;\n            --mv-warn:#ee9b19;\n            --mv-danger:#d83838;\n            font-family:\"Roboto\", \"Inter\", -apple-system, BlinkMacSystemFont, \"Helvetica Neue\", Helvetica, Arial, sans-serif;\n            color:var(--mv-text);\n            background:var(--mv-bg);\n            border-radius:0;\n            overflow:hidden;\n            font-kerning:normal;\n            font-variant-numeric:tabular-nums lining-nums;\n            font-feature-settings:\"tnum\" 1, \"kern\" 1;\n            text-rendering:optimizeLegibility;\n            -webkit-font-smoothing:antialiased;\n            -moz-osx-font-smoothing:grayscale;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 * { box-sizing:border-box; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 a { color:inherit; }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-play {\n            border:0;\n            cursor:pointer;\n            color:#fff;\n            font-family:\"Roboto\", \"Inter\", sans-serif;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-play:disabled {\n            cursor:wait;\n            opacity:.55;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-radar-source {\n            margin-top:4px;\n            font-size:10px;\n            color:rgba(255,255,255,.74);\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-place-weather {\n            display:inline-flex;\n            align-items:center;\n            justify-content:center;\n            gap:5px;\n            margin-top:4px;\n            min-height:24px;\n            padding:4px 8px;\n            background:rgba(17,24,39,0.85);\n            backdrop-filter: blur(4px);\n            border:1px solid rgba(255,255,255,.2);\n            border-radius:12px;\n            color:#fff;\n            font-size:12px;\n            font-weight:600;\n            text-shadow:none;\n            white-space:nowrap;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-weather-symbol {\n            display:inline-flex;\n            align-items:center;\n            justify-content:center;\n            min-width:18px;\n            font-size:16px;\n            line-height:1;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-weather-symbol svg {\n            width:1.2em; height:1.2em;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wind-arrow {\n            display:inline-flex;\n            align-items:center;\n            justify-content:center;\n            width:16px;\n            height:16px;\n        }\n        \n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wind-arrow svg {\n            width:100%;\n            height:100%;\n            fill:currentColor;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-head {\n            display:flex;\n            align-items:center;\n            justify-content:space-between;\n            gap:16px;\n            padding:14px 24px;\n            background:#ffffff;\n            border-bottom:1px solid var(--mv-line);\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-brand {\n            display:flex;\n            align-items:center;\n            gap:16px;\n            min-width:0;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-crest {\n            width:56px;\n            height:auto;\n            max-height:72px;\n            object-fit:contain;\n            display:block;\n            flex:0 0 auto;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-title {\n            margin:0;\n            color:#0d4f91;\n            font-size:38px;\n            line-height:1.12;\n            font-weight:600;\n            letter-spacing:0;\n            text-transform:none;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-subtitle {\n            margin-top:6px;\n            color:#2e74bd;\n            font-size:20px;\n            line-height:1.2;\n            font-weight:400;\n            letter-spacing:0;\n            text-transform:uppercase;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-updated {\n            color:#7a8898;\n            font-size:12px;\n            font-weight:600;\n            white-space:nowrap;\n            text-align:right;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-updated strong {\n            color:#0d3974;\n            font-size:13px;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-map-wrap {\n            position:relative;\n            padding:14px 14px 0;\n            background:var(--mv-bg);\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-map-frame {\n            position:relative;\n            height:clamp(460px, calc(100vh - 170px), 820px);\n            height:clamp(460px, calc(100svh - 170px), 820px);\n            background:#dfe8ef;\n            border-radius:24px;\n            overflow:hidden;\n            box-shadow:var(--mv-shadow);\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-map {\n            position:absolute;\n            inset:0;\n            width:100%;\n            height:100%;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-layer-menu-wrap {\n            padding:0 14px;\n            background:var(--mv-bg);\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-layer-menu {\n            display:grid;\n            grid-template-columns:repeat(4,minmax(0,1fr));\n            background:#ffffff;\n            border:1px solid var(--mv-line);\n            border-radius:20px;\n            box-shadow:0 1px 0 rgba(13,79,145,.06);\n            overflow: hidden;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-layer-btn,\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-layer-link {\n            appearance:none;\n            display:flex;\n            align-items:center;\n            justify-content:center;\n            gap:7px;\n            min-width:0;\n            min-height:48px;\n            padding:8px 9px;\n            border:0;\n            border-right:1px solid var(--mv-line);\n            background:#ffffff;\n            color:#16385f;\n            text-decoration:none;\n            font-family:inherit;\n            font-size:12px;\n            font-weight:600;\n            line-height:1.15;\n            text-align:center;\n            cursor:pointer;\n            transition:background .14s ease,color .14s ease;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-layer-menu > :last-child {\n            border-right:0;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-layer-btn:hover,\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-layer-link:hover {\n            background:#f1f6fb;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-layer-btn.is-active {\n            background:var(--mv-blue-2);\n            color:#fff;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-layer-icon {\n            display:flex;\n            align-items:center;\n            font-size:16px;\n            line-height:1;\n            flex:0 0 auto;\n        }\n        \n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-layer-icon svg { width:1.2em; height:1.2em; }\n\n        \/* Floating Radar Controls *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-radar-controls {\n            display:none;\n            position:absolute;\n            bottom:24px;\n            left:50%;\n            transform:translateX(-50%);\n            z-index:999;\n            width:90%;\n            max-width:540px;\n            margin:0;\n            padding:12px 20px 14px;\n            background:rgba(13, 79, 145, 0.85);\n            backdrop-filter:blur(12px);\n            -webkit-backdrop-filter:blur(12px);\n            border-radius:100px;\n            color:#fff;\n            border:1px solid rgba(255,255,255,0.15);\n            box-shadow:0 8px 32px rgba(0,0,0,0.25);\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-radar-controls.is-visible {\n            display:block;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-radar-row {\n            display:grid;\n            grid-template-columns:36px 48px minmax(0,1fr) 48px 58px;\n            gap:12px;\n            align-items:center;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-play {\n            width:36px;\n            height:36px;\n            display:flex;\n            align-items:center;\n            justify-content:center;\n            border:none;\n            border-radius:50%;\n            background:rgba(255,255,255,0.2);\n            color:#fff;\n            font-family:inherit;\n            font-size:14px;\n            cursor:pointer;\n            transition:background 0.2s;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-play:hover:not(:disabled) {\n            background:rgba(255,255,255,0.3);\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-play:disabled {\n            cursor:wait;\n            opacity:.45;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-radar-time,\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-radar-current {\n            font-size:11px;\n            font-weight:600;\n            color:rgba(255,255,255,.82);\n            text-align:center;\n            white-space:nowrap;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-radar-current {\n            color:#fff;\n            font-size:12px;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-radar-range {\n            width:100%;\n            min-width:0;\n            height:36px;\n            margin:0;\n            accent-color:#66a9ff;\n            cursor:pointer;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-radar-source {\n            margin-top:6px;\n            font-size:10px;\n            color:rgba(255,255,255,.68);\n            text-align:center;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-grid {\n            display:grid;\n            grid-template-columns:repeat(12, minmax(0, 1fr));\n            gap:24px;\n            padding:24px 14px;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-span-3 { grid-column:span 3; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-span-4 { grid-column:span 4; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-span-5 { grid-column:span 5; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-span-12 { grid-column:span 12; }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card {\n            background:var(--mv-card);\n            border:1px solid var(--mv-line);\n            border-radius:24px;\n            padding:24px;\n            min-width:0;\n            box-shadow:var(--mv-shadow);\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-title {\n            margin:0 0 16px;\n            color:#164782;\n            font-size:14px;\n            font-weight:600;\n            letter-spacing:.02em;\n            text-transform:uppercase;\n            display:flex;\n            align-items:center;\n            gap:8px;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-now {\n            display:flex;\n            align-items:center;\n            gap:20px;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-now-icon {\n            font-size:72px;\n            line-height:1;\n            display:flex;\n            align-items:center;\n            justify-content:center;\n        }\n        \n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-now-icon svg { width:1em; height:1em; }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-now-temp {\n            font-size:64px;\n            line-height:1;\n            font-weight:600;\n            color:#093b7a;\n            letter-spacing:-.04em;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-muted {\n            color:var(--mv-muted);\n            font-size:13px;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-kv {\n            display:flex;\n            justify-content:space-between;\n            gap:10px;\n            padding:10px 0;\n            border-bottom:1px solid #edf2f6;\n            font-size:14px;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-kv:last-child { border-bottom:0; }\n        \n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-kv-label {\n            display:flex; align-items:center; gap:6px;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-days {\n            display:grid;\n            grid-template-columns:repeat(7, minmax(72px, 1fr));\n            gap:8px;\n            overflow-x:auto;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-day {\n            padding:12px 8px;\n            background:#f6f8fa;\n            border-radius:16px;\n            text-align:center;\n            min-width:72px;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-day.is-today { background:#fffaf4; box-shadow:inset 0 4px 0 #ef7d22; }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-day-top { font-weight:600; color:#16385f; font-size:12px; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-day-date { font-size:11px; color:#8493a2; margin-top:2px; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-day-icon { font-size:36px; margin:12px 0; display:flex; justify-content:center; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-day-icon svg { width:1em; height:1em; }\n        \n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-max { color:#e23d38; font-size:18px; font-weight:600; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-min { color:#205ba2; font-size:18px; font-weight:600; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-precip-small { color:#2560a8; font-size:12px; margin-top:8px; display:block; }\n\n        \/* =========================================================\n         *  VODOSTAJI \u2013 zajedni\u010dki raspored kartice (Sava + Odra\/Kupa)\n         *  Jedan sustav: naziv \u2192 svje\u017eina \u2192 razina \u2192 promjena \u2192\n         *  traka pragova \u2192 status \u2192 graf.\n         *  Podloga kartice = rang rasta (naran\u010dasta\u2192crvena za najve\u0107i rast);\n         *  traka pragova i oznaka stanja = slu\u017ebeno stanje obrane od poplava.\n         * ========================================================= *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap {\n            display:grid;\n            grid-template-columns:repeat(5,minmax(0,1fr));\n            gap:16px;\n            align-items:stretch;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap.mv-water-secondary {\n            grid-template-columns:repeat(2,minmax(0,1fr));\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-sava-head {\n            display:flex;\n            align-items:center;\n            justify-content:space-between;\n            gap:10px 14px;\n            flex-wrap:wrap;\n            margin:0 0 16px;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-sava-head .mv-card-title { margin:0; }\n\n        \/* Ozbiljan, ravni segmentirani prekida\u010d (bez oslanjanja na zaobljene rubove, jer ih\n           globalno pravilo #mvmeteo... border-radius:0 !important ionako uklanja). Razdjelnici\n           izme\u0111u tipki i puna tamnoplava pozadina aktivne tipke daju jasan, \"kontrolni\" izgled\n           umjesto dojma nedovr\u0161enog elementa. *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-range-wrap { display:inline-flex; flex-direction:column; gap:6px; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-range-label {\n            color:#6f8398;\n            font-size:11px;\n            line-height:1.2;\n            font-weight:700;\n            letter-spacing:.06em;\n            text-transform:uppercase;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-range {\n            display:inline-flex;\n            border:1px solid #cfd9e3;\n            background:#f7f9fb;\n            overflow:hidden;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-range button {\n            appearance:none;\n            border:0;\n            border-right:1px solid #cfd9e3;\n            background:transparent;\n            min-height:34px;\n            padding:7px 12px;\n            font:inherit;\n            font-size:12px;\n            font-weight:700;\n            color:#4d6178;\n            cursor:pointer;\n            white-space:nowrap;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-range button:last-child { border-right:0; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-range button:hover:not(.is-active) { background:#eef3f8; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-range button.is-active {\n            background:#0b3d78;\n            color:#fff;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-range button:focus-visible,\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-node:focus-visible,\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-link:focus-visible,\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-help summary:focus-visible {\n            outline:2px solid #145aa5;\n            outline-offset:2px;\n        }\n\n        \/* ---- Pregled toka Save (uzvodno \u2192 nizvodno) ---- *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river {\n            margin:0 0 16px;\n            padding:14px 14px 12px;\n            border:1px solid #e7edf4;\n            border-radius:22px;\n            background:#fff;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-dir {\n            display:flex;\n            justify-content:space-between;\n            gap:8px;\n            margin-bottom:10px;\n            color:#6f8398;\n            font-size:10.5px;\n            line-height:1.2;\n            font-weight:700;\n            letter-spacing:.09em;\n            text-transform:uppercase;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-dir-mid { color:#9aabbb; font-weight:600; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-nodes {\n            position:relative;\n            display:grid;\n            grid-template-columns:repeat(5,minmax(0,1fr));\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-nodes::before {\n            content:'';\n            position:absolute;\n            left:0;\n            right:6px;\n            top:9px;\n            height:3px;\n            border-radius:3px;\n            background:linear-gradient(90deg,#d2e3f4 0%,#7fa9d4 100%);\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-nodes::after {\n            content:'';\n            position:absolute;\n            right:0;\n            top:4px;\n            border-left:9px solid #7fa9d4;\n            border-top:6.5px solid transparent;\n            border-bottom:6.5px solid transparent;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-node {\n            appearance:none;\n            position:relative;\n            display:flex;\n            flex-direction:column;\n            align-items:center;\n            gap:2px;\n            min-width:0;\n            padding:0 1px;\n            border:0;\n            background:none;\n            font:inherit;\n            color:inherit;\n            text-align:center;\n            cursor:pointer;\n            border-radius:12px;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-dot {\n            position:relative;\n            z-index:1;\n            width:21px;\n            height:21px;\n            box-sizing:border-box;\n            border-radius:50%;\n            background:#fff;\n            border:5px solid #7fa9d4;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-dot.is-info { border-color:#a9b8c7; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-dot.is-preparation { border-color:#e2b619; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-dot.is-regular { border-color:#ee8a2b; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-dot.is-extraordinary,\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-dot.is-emergency { border-color:#d24545; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-dot.is-unavailable { border:4px dashed #c3ced9; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-name {\n            margin-top:7px;\n            max-width:100%;\n            color:#4d6178;\n            font-size:11.5px;\n            line-height:1.2;\n            font-weight:600;\n            overflow-wrap:anywhere;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-level {\n            color:#0b3d78;\n            font-size:20px;\n            line-height:1.1;\n            font-weight:800;\n            letter-spacing:-.03em;\n            white-space:nowrap;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-level small {\n            margin-left:2px;\n            color:#6b7f93;\n            font-size:10.5px;\n            font-weight:600;\n            letter-spacing:0;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-chg {\n            min-height:15px;\n            color:#5b6f82;\n            font-size:11.5px;\n            line-height:1.3;\n            font-weight:700;\n            white-space:nowrap;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-chg.is-up { color:#d96e16; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-chg.is-down { color:#2678ad; }\n\n        \/* ---- Kartica postaje ---- *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-box {\n            position:relative;\n            display:flex;\n            flex-direction:column;\n            border:1px solid #e7edf4;\n            border-radius:28px;\n            padding:22px;\n            background:linear-gradient(180deg,#ffffff 0%,#f8fafc 100%);\n            box-shadow:0 8px 24px rgba(17,24,39,0.04);\n            scroll-margin-top:72px;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-box:focus { outline:none; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-box:focus-visible { outline:2px solid #145aa5; outline-offset:3px; }\n\n        \/* Rang rasta (dinami\u010dki): 1. mjesto = naran\u010dasta koja s ja\u010dinom porasta prelazi u crvenu\n           (boje ra\u010duna JS preko --mv-rise-*), 2. = be\u017e, 3. = svjetloplava. *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-box.is-rise-1 {\n            background:linear-gradient(180deg,var(--mv-rise-bg-1,#fff8ef) 0%,var(--mv-rise-bg-2,#fff1e2) 100%);\n            border-color:var(--mv-rise-border,#efbd8d);\n            box-shadow:0 10px 28px var(--mv-rise-shadow,rgba(239,125,34,0.10));\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-box.is-rise-2 {\n            background:linear-gradient(180deg,#fffdf8 0%,#f7efe4 100%);\n            border-color:#ead8c2;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-box.is-rise-3 {\n            background:linear-gradient(180deg,#f8fbff 0%,#edf5fc 100%);\n            border-color:#cfe1f1;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-box.is-rise-1 .mv-water-history-area { fill:var(--mv-rise-accent,#ef7d22); }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-box.is-rise-1 .mv-water-history-band { fill:var(--mv-rise-accent,#ef7d22); opacity:.18; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-box.is-rise-1 .mv-water-history-line { stroke:var(--mv-rise-accent,#ef7d22); }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-box.is-rise-1 .mv-water-history-dot { fill:var(--mv-rise-accent,#ef7d22); }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-box.is-rise-2 .mv-water-history-area { fill:#b78b5c; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-box.is-rise-2 .mv-water-history-band { fill:#b78b5c; opacity:.18; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-box.is-rise-2 .mv-water-history-line { stroke:#b78b5c; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-box.is-rise-2 .mv-water-history-dot { fill:#b78b5c; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-box.is-rise-3 .mv-water-history-area { fill:#5f93c5; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-box.is-rise-3 .mv-water-history-band { fill:#5f93c5; opacity:.18; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-box.is-rise-3 .mv-water-history-line { stroke:#5f93c5; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-box.is-rise-3 .mv-water-history-dot { fill:#5f93c5; }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-top {\n            display:flex;\n            align-items:center;\n            justify-content:space-between;\n            flex-wrap:wrap;\n            gap:6px 10px;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-name {\n            font-size:17px;\n            line-height:1.2;\n            font-weight:600;\n            letter-spacing:-0.01em;\n            color:#16385f;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-pos {\n            padding:3px 9px;\n            border-radius:999px;\n            background:#eef3f8;\n            color:#5f748a;\n            font-size:10.5px;\n            line-height:1.3;\n            font-weight:700;\n            letter-spacing:.06em;\n            text-transform:uppercase;\n            white-space:nowrap;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-context {\n            margin-top:3px;\n            color:#64748b;\n            font-size:10px;\n            line-height:1.35;\n            font-weight:600;\n            letter-spacing:.015em;\n        }\n\n        \/* Svje\u017eina mjerenja *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-fresh {\n            display:flex;\n            align-items:flex-start;\n            gap:7px;\n            margin-top:7px;\n            color:#5b6f82;\n            font-size:12.5px;\n            line-height:1.4;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-fresh-dot {\n            flex:0 0 8px;\n            width:8px;\n            height:8px;\n            margin-top:5px;\n            border-radius:50%;\n            background:#2ea34a;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-fresh.is-latest .mv-fresh-dot { background:#e2a419; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-fresh.is-stale .mv-fresh-dot { background:#a9b8c7; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-fresh.is-stale { color:#8a5a12; }\n\n        \/* 1. Glavni vodostaj + strelica smjera *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-levelrow {\n            display:flex;\n            align-items:flex-end;\n            justify-content:space-between;\n            gap:10px;\n            margin-top:14px;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-level {\n            display:flex;\n            align-items:flex-end;\n            gap:8px;\n            line-height:1;\n            white-space:nowrap;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-level-value {\n            display:inline-block;\n            font-size:48px;\n            line-height:.88;\n            font-weight:800;\n            letter-spacing:-0.055em;\n            color:#0b3d78;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-level-unit {\n            display:inline-block;\n            padding-bottom:6px;\n            font-size:18px;\n            line-height:1;\n            font-weight:600;\n            color:#536b82;\n            letter-spacing:0;\n            text-transform:lowercase;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-level-unavailable {\n            font-size:17px;\n            line-height:1.3;\n            font-weight:600;\n            color:#7d8d9c;\n        }\n\n        \/* Oznaka ranga rasta (plava\/be\u017e\/naran\u010dasta-crvena boja prati podlogu kartice) *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-rank {\n            display:none;\n            align-self:flex-start;\n            margin-top:12px;\n            padding:5px 11px;\n            border-radius:999px;\n            font-size:11.5px;\n            line-height:1.25;\n            font-weight:700;\n            letter-spacing:.02em;\n            white-space:nowrap;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-rank.is-visible { display:inline-flex; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-box.is-rise-1 .mv-water-rank { background:var(--mv-rise-accent,#ef7d22); color:#fff; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-box.is-rise-2 .mv-water-rank { background:#f0e2cf; color:#7a5730; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-box.is-rise-3 .mv-water-rank { background:#dfeaf6; color:#2d5f93; }\n\n        \/* 2. Promjena \u2013 uvijek s vremenskom osnovom *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-changes {\n            margin-top:16px;\n            border-top:1px solid #e7edf4;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-change {\n            display:flex;\n            align-items:center;\n            justify-content:space-between;\n            gap:10px;\n            padding:8px 0;\n            border-bottom:1px solid #eef2f6;\n            color:#5b6f82;\n            font-size:12.5px;\n            line-height:1.3;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-change strong {\n            color:#0b3d78;\n            font-size:14px;\n            font-weight:700;\n            white-space:nowrap;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-change strong {\n            display:inline-flex;\n            align-items:center;\n            gap:6px;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-change strong b { font-weight:700; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-change strong svg { flex:0 0 17px; }\n        \/* Boje smjera: rast = naran\u010dasta, pad = plava, stagnacija = siva (kao u detaljnom bloku Dubrov\u010dak). *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-change strong.is-up { color:#d96e16; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-change strong.is-down { color:#2678ad; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-change strong.is-flat { color:#71849a; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-change strong.is-none { color:#94a3b8; font-weight:600; }\n\n        \/* 3. Traka pragova obrane od poplava *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-gauge { margin-top:16px; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-gauge-track {\n            position:relative;\n            height:10px;\n            border-radius:999px;\n            background:#d6e6f5;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-gauge-tick {\n            position:absolute;\n            top:0;\n            bottom:0;\n            width:2px;\n            margin-left:-1px;\n            background:#fff;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-gauge-marker {\n            position:absolute;\n            top:50%;\n            width:18px;\n            height:18px;\n            box-sizing:border-box;\n            margin:-9px 0 0 -9px;\n            border-radius:50%;\n            background:#fff;\n            border:3px solid #0b3d78;\n            box-shadow:0 2px 6px rgba(11,61,120,.35);\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-gauge-caption {\n            display:flex;\n            align-items:baseline;\n            justify-content:space-between;\n            gap:8px;\n            margin-top:10px;\n            color:#5b6f82;\n            font-size:12.5px;\n            line-height:1.3;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-gauge-caption strong {\n            color:#0b3d78;\n            font-size:13.5px;\n            font-weight:700;\n            white-space:nowrap;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-gauge-none {\n            margin-top:16px;\n            color:#7d8e9f;\n            font-size:12.5px;\n            line-height:1.4;\n        }\n\n        \/* 5. Dodatni podaci: DHMZ \/ protok \/ temperatura vode *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-extra {\n            margin-top:12px;\n            color:#50677e;\n            font-size:12.5px;\n            line-height:1.45;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-extra:empty { display:none; }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-link {\n            appearance:none;\n            align-self:flex-start;\n            margin-top:12px;\n            padding:0;\n            border:0;\n            background:none;\n            font:inherit;\n            font-size:12.5px;\n            font-weight:700;\n            color:#145aa5;\n            text-decoration:underline;\n            text-underline-offset:3px;\n            cursor:pointer;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-changes:empty { display:none; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-change.is-selected { background:#eef4fa; margin:0 -8px; padding-left:8px; padding-right:8px; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-change.is-selected > span { color:#16385f; font-weight:600; }\n\n        \/* Velika strelica uz glavni broj: smjer i ja\u010dina promjene od zadnjeg mjerenja. *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-arrow {\n            display:none;\n            flex:0 0 44px;\n            align-items:center;\n            justify-content:center;\n            width:44px;\n            height:44px;\n            background:#eef2f6;\n            color:#71849a;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-arrow.is-visible { display:inline-flex; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-arrow.is-up { background:#fdeedf; color:#d96e16; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-arrow.is-down { background:#e3eff8; color:#2678ad; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-arrow svg { width:26px; height:26px; }\n\n        \/* Najve\u0107i brojevi: Bahnschrift Condensed 500 (Windows). Na sustavima bez Bahnschrifta\n           koristi se najbli\u017ei uski sistemski font. *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-level-value,\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-level,\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-now-temp,\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-aqi-number,\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-uv-number,\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-kpi-value.is-main,\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-24h-summary-value {\n            font-family:\"Bahnschrift Condensed\",\"Bahnschrift\",\"Roboto Condensed\",\"Arial Narrow\",\"Helvetica Neue\",sans-serif !important;\n            font-stretch:condensed;\n            font-weight:500 !important;\n            letter-spacing:-0.005em !important;\n            font-variant-numeric:tabular-nums;\n        }\n\n\/* 5. STATUS JE UVIJEK POSLJEDNJA INFORMACIJA *\/\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-status-wrap {\n    margin-top:16px;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-status {\n    display:inline-flex;\n    align-items:center;\n    gap:8px;\n    margin:0;\n    padding:9px 13px;\n    border:1px solid #dbe5ee;\n    border-radius:999px;\n    background:#f4f8fb;\n    color:#385a73;\n    font-size:11px;\n    line-height:1.15;\n    font-weight:700;\n    letter-spacing:.035em;\n    text-transform:uppercase;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-status-icon {\n    display:inline-flex;\n    align-items:center;\n    justify-content:center;\n    width:19px;\n    height:19px;\n    border-radius:50%;\n    background:#fff;\n    border:1px solid #dbe5ee;\n    flex:0 0 19px;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-status-text {\n    line-height:1.15;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-status.is-warn {\n    background:#fff8eb;\n    border-color:#f3ddb4;\n    color:#9b6b10;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-status.is-danger {\n    background:#fff2f2;\n    border-color:#efcaca;\n    color:#b54747;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-measure-time {\n    margin-top:14px;\n    color:#94a3b8;\n    font-size:11px;\n    line-height:1.35;\n}\n\n\n\/* 6. MINI GRAFOVI VODOSTAJA \u2013 prekida\u010d 24 h \/ 30 dana (jedan graf po kartici) *\/\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-history {\n    margin-top:auto;\n    padding-top:16px;\n}\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72[data-water-range=\"24h\"] .mv-water-history-block.is-daily { display:none; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72[data-water-range=\"30d\"] .mv-water-history-block.is-hourly { display:none; }\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-history-block {\n    padding-top:14px;\n    border-top:1px solid #e7edf4;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-history-head {\n    display:flex;\n    flex-direction:column;\n    align-items:flex-start;\n    gap:3px;\n    margin-bottom:8px;\n    color:#6f8398;\n    font-size:11px;\n    line-height:1.25;\n    font-weight:700;\n    letter-spacing:.03em;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-history-stats {\n    display:block;\n    width:100%;\n    color:#5b6f82;\n    font-size:12px;\n    font-weight:500;\n    letter-spacing:0;\n    line-height:1.35;\n    white-space:normal;\n    overflow-wrap:anywhere;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-history-chart {\n    display:block;\n    width:100%;\n    height:64px;\n    overflow:visible;\n}\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-history-block.is-hourly .mv-water-history-chart { height:64px; }\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-history-grid {\n    stroke:#e6edf4;\n    stroke-width:1;\n    vector-effect:non-scaling-stroke;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-history-area { fill:#2e74bd; opacity:.08; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-history-band { fill:#2e74bd; opacity:.16; stroke:none; }\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-history-line {\n    fill:none;\n    stroke:#2e74bd;\n    stroke-width:2;\n    stroke-linecap:round;\n    stroke-linejoin:round;\n    vector-effect:non-scaling-stroke;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-history-dot { fill:#2e74bd; }\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-history-threshold-line {\n    stroke:#d4a017;\n    stroke-width:1;\n    stroke-dasharray:3 3;\n    opacity:.85;\n    vector-effect:non-scaling-stroke;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-history-threshold {\n    margin-top:6px;\n    color:#6f8398;\n    font-size:11.5px;\n    line-height:1.3;\n}\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-history-threshold strong { color:#4d6178; font-weight:700; }\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-history-dates {\n    display:flex;\n    justify-content:space-between;\n    gap:8px;\n    margin-top:3px;\n    color:#8595a5;\n    font-size:11px;\n    line-height:1.2;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-history-empty {\n    min-height:64px;\n    display:flex;\n    align-items:center;\n    color:#8595a5;\n    font-size:12px;\n    line-height:1.4;\n}\n\n\/* Legenda pragova + \u201eKako \u010ditati prikaz\u201d *\/\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-gauge-legend {\n    display:flex;\n    flex-wrap:wrap;\n    align-items:center;\n    gap:6px 14px;\n    margin-top:18px;\n    color:#5b6f82;\n    font-size:12px;\n    line-height:1.3;\n}\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-gauge-legend-title { color:#4d6178; font-weight:700; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-gauge-legend .mv-swatch {\n    display:inline-block;\n    width:16px;\n    height:8px;\n    margin-right:6px;\n    border-radius:4px;\n    vertical-align:middle;\n}\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-help {\n    margin-top:14px;\n    padding-top:12px;\n    border-top:1px solid #e7edf4;\n}\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-help summary {\n    display:inline-flex;\n    align-items:center;\n    gap:8px;\n    color:#164782;\n    font-size:13px;\n    font-weight:700;\n    cursor:pointer;\n    list-style:none;\n}\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-help summary::-webkit-details-marker { display:none; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-help summary::before {\n    content:'i';\n    display:inline-flex;\n    align-items:center;\n    justify-content:center;\n    width:18px;\n    height:18px;\n    border-radius:50%;\n    border:1.5px solid #164782;\n    border-radius:0;\n    font-size:11px;\n    font-weight:800;\n    font-style:normal;\n    line-height:1;\n}\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-help[open] summary::before { background:#164782; color:#fff; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-help ul {\n    margin:10px 0 0;\n    padding-left:18px;\n    color:#50677e;\n    font-size:12.5px;\n    line-height:1.55;\n}\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-help li + li { margin-top:5px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-help .mv-source-note { margin-top:10px; }\n\n\/* Kad je barem jedna postaja rangirana, red s oznakom zauzima mjesto na svim karticama u mre\u017ei (poravnanje razina). *\/\n@media (min-width:701px) {\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-sava.has-rank .mv-water-rank { display:inline-flex; align-items:center; min-height:27px; visibility:hidden; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-sava.has-rank .mv-water-rank.is-visible { visibility:visible; }\n}\n@media (min-width:701px) and (max-width:1100px) {\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap.mv-water-sava { grid-template-columns:repeat(6,minmax(0,1fr)); }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap.mv-water-sava .mv-water-box { grid-column:span 2; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap.mv-water-sava .mv-water-box:nth-child(n+4) { grid-column:span 3; }\n}\n\n\/* \u0160iroki zaslon: pregled toka postaje traka to\u010daka to\u010dno iznad kartica *\/\n@media (min-width:1101px) {\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river { padding:0; border:0; border-radius:0; background:transparent; margin-bottom:10px; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-nodes { gap:16px; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-name,\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-level,\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-chg { display:none; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-dir { margin-bottom:8px; }\n}\n\n@media (max-width:650px) {\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river { padding:12px 8px 10px; border-radius:20px; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-dir { padding:0 6px; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-name { font-size:10.5px; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-level { font-size:17px; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-level small { display:none; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-river-chg { font-size:11px; }\n}\n\n\/* 7. DUBROV\u010cAK \u2013 detaljni hidrolo\u0161ki prikaz *\/\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-dubrovacak-detail {\n    padding:24px;\n    overflow:hidden;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-dubrovacak-charts {\n    padding:24px;\n    overflow:hidden;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-dubrovacak-charts .mv-dub-section {\n    margin-top:0;\n    padding-top:0;\n    border-top:0;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-detail-head {\n    display:flex;\n    justify-content:space-between;\n    align-items:flex-start;\n    gap:20px;\n    margin-bottom:18px;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-detail-title {\n    margin:0;\n    color:#173f73;\n    font-size:18px;\n    line-height:1.2;\n    font-weight:750;\n    letter-spacing:.01em;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-detail-subtitle {\n    margin-top:5px;\n    color:#7c8e9f;\n    font-size:11px;\n    line-height:1.4;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-detail-status {\n    margin-top:9px;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-detail-status .mv-water-status {\n    padding:6px 10px;\n    font-size:9px;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-detail-status .mv-water-status-icon {\n    width:17px;\n    height:17px;\n    flex-basis:17px;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-clockbox {\n    flex:0 0 auto;\n    min-width:154px;\n    padding:10px 13px;\n    border:1px solid #dfe8f0;\n    border-radius:13px;\n    background:#f8fbfd;\n    text-align:right;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-clockbox span {\n    display:block;\n    color:#8b9aaa;\n    font-size:9px;\n    line-height:1.2;\n    font-weight:700;\n    letter-spacing:.08em;\n    text-transform:uppercase;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-clockbox strong {\n    display:block;\n    margin-top:2px;\n    color:#173f73;\n    font-variant-numeric:tabular-nums;\n    font-size:22px;\n    line-height:1.1;\n    font-weight:700;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-kpis {\n    display:grid;\n    grid-template-columns:1.15fr .9fr .9fr 1.35fr;\n    gap:10px;\n    margin-bottom:18px;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-kpi {\n    min-width:0;\n    padding:13px 14px;\n    border:1px solid #e2e9f0;\n    border-radius:14px;\n    background:#fff;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-kpi-label {\n    display:block;\n    color:#8a9aaa;\n    font-size:9px;\n    line-height:1.2;\n    font-weight:700;\n    letter-spacing:.06em;\n    text-transform:uppercase;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-kpi-value {\n    display:block;\n    margin-top:5px;\n    color:#173f73;\n    font-size:21px;\n    line-height:1.15;\n    font-weight:700;\n    font-variant-numeric:tabular-nums;\n    white-space:normal;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-kpi-value.is-main {\n    font-size:31px;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-rates {\n    display:grid;\n    grid-template-columns:repeat(3,minmax(0,1fr));\n    gap:10px;\n    margin:-6px 0 18px;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-rate {\n    min-width:0;\n    padding:12px 14px;\n    border:1px solid #dfe8f0;\n    border-radius:14px;\n    background:#f8fbfd;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-rate-label {\n    display:block;\n    color:#7f90a1;\n    font-size:9px;\n    line-height:1.25;\n    font-weight:750;\n    letter-spacing:.055em;\n    text-transform:uppercase;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-rate-value {\n    display:block;\n    margin-top:5px;\n    color:#173f73;\n    font-size:22px;\n    line-height:1.1;\n    font-weight:750;\n    font-variant-numeric:tabular-nums;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-rate-note {\n    grid-column:1 \/ -1;\n    margin:-2px 2px 0;\n    color:#92a0ad;\n    font-size:9.5px;\n    line-height:1.4;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-section {\n    margin-top:18px;\n    padding-top:17px;\n    border-top:1px solid #e8eef4;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-section-head {\n    display:flex;\n    justify-content:space-between;\n    align-items:flex-end;\n    gap:14px;\n    margin-bottom:10px;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-section-title {\n    color:#415a72;\n    font-size:11px;\n    line-height:1.3;\n    font-weight:750;\n    letter-spacing:.06em;\n    text-transform:uppercase;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-section-note {\n    color:#98a6b4;\n    font-size:10px;\n    line-height:1.35;\n    text-align:right;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-cross-wrap {\n    position:relative;\n    border:1px solid #e1e9f0;\n    border-radius:16px;\n    background:linear-gradient(180deg,#f8fbfe 0%,#ffffff 100%);\n    overflow:hidden;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-cross-svg {\n    display:block;\n    width:100%;\n    height:auto;\n    min-height:280px;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-cross-legend {\n    display:flex;\n    flex-wrap:wrap;\n    gap:8px 14px;\n    padding:10px 14px 12px;\n    border-top:1px solid #edf2f6;\n    color:#667b8f;\n    font-size:10px;\n    line-height:1.3;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-cross-legend span {\n    display:inline-flex;\n    align-items:center;\n    gap:5px;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-legend-line {\n    width:18px;\n    height:2px;\n    border-radius:2px;\n    background:#2e74bd;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-legend-line.prep { background:#d4a017; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-legend-line.regular { background:#ef8b2c; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-legend-line.extra { background:#dd5a32; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-legend-line.emergency { background:#c62f38; }\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-charts {\n    display:grid;\n    grid-template-columns:1fr;\n    gap:14px;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-24h-summary {\n    display:grid;\n    grid-template-columns:repeat(3,minmax(0,1fr));\n    gap:10px;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-24h-summary-item {\n    border:1px solid #e1e9f0;\n    border-radius:14px;\n    background:#f8fbfd;\n    padding:12px 14px;\n    min-width:0;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-24h-summary-label {\n    display:block;\n    color:#7b8e9f;\n    font-size:9px;\n    line-height:1.25;\n    font-weight:800;\n    letter-spacing:.05em;\n    text-transform:uppercase;\n    margin-bottom:4px;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-24h-summary-value {\n    display:block;\n    color:#173f73;\n    font-size:22px;\n    line-height:1.05;\n    font-weight:800;\n    font-variant-numeric:tabular-nums;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-24h-summary-time {\n    display:block;\n    margin-top:4px;\n    color:#8b9aaa;\n    font-size:9px;\n    line-height:1.25;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-24h-summary-item.is-change .mv-dub-24h-summary-value.is-up { color:#d96e16; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-24h-summary-item.is-change .mv-dub-24h-summary-value.is-down { color:#2678ad; }\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-chart-card {\n    border:1px solid #e1e9f0;\n    border-radius:16px;\n    background:#fff;\n    padding:14px 14px 10px;\n    overflow:hidden;\n}\n\n\n\/* Dubrov\u010dak \u00b7 sa\u017eetak tendencije umjesto velikog stup\u010dastog grafa promjene. *\/\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-trend-status { padding:16px 18px 17px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-head { display:flex; justify-content:space-between; align-items:flex-start; gap:16px; padding-bottom:12px; border-bottom:1px solid #e7edf4; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-source { color:#8293a3; font-size:10px; line-height:1.3; text-align:right; white-space:nowrap; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-lead { display:grid; grid-template-columns:1.15fr .85fr; gap:0; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-direction,\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-safety { padding:18px 0 16px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-direction { padding-right:24px; border-right:1px solid #e7edf4; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-safety { padding-left:24px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-direction > span,\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-safety > span,\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-stats span { display:block; color:#6f8398; font-size:10px; font-weight:700; letter-spacing:.08em; text-transform:uppercase; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-direction > strong { display:inline-block; margin-top:7px; color:#0b3d78; font-size:30px; line-height:1; font-weight:800; letter-spacing:.01em; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-direction > b { display:inline-block; margin-left:12px; color:#0b3d78; font-size:22px; line-height:1; font-weight:600; font-family:\"Bahnschrift Condensed\",\"Bahnschrift\",\"Roboto Condensed\",\"Arial Narrow\",sans-serif; font-stretch:condensed; font-variant-numeric:tabular-nums; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-direction .is-up,\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-stats strong.is-up { color:#d96e16; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-direction .is-down,\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-stats strong.is-down { color:#2678ad; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-direction .is-flat { color:#65798d; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-direction p { margin:9px 0 0; color:#65798d; font-size:12px; line-height:1.45; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-safety > strong { display:block; margin-top:7px; color:#173f73; font-size:18px; line-height:1.15; font-weight:800; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-safety > div { display:flex; align-items:baseline; justify-content:space-between; gap:12px; margin-top:14px; padding-top:12px; border-top:1px solid #edf1f5; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-safety > div span { color:#6f8398; font-size:11px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-safety > div b { color:#0b3d78; font-size:26px; font-weight:500; font-family:\"Bahnschrift Condensed\",\"Bahnschrift\",\"Roboto Condensed\",\"Arial Narrow\",sans-serif; font-stretch:condensed; font-variant-numeric:tabular-nums; white-space:nowrap; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-safety small { display:block; margin-top:4px; color:#8b9aaa; font-size:10px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-stats { display:grid; grid-template-columns:repeat(3,minmax(0,1fr)); border-top:1px solid #e7edf4; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-stats > div { padding:15px 18px 2px 0; min-width:0; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-stats > div:not(:first-child) { padding-left:18px; border-left:1px solid #e7edf4; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-stats strong { display:block; margin-top:6px; color:#173f73; font-size:24px; line-height:1; font-weight:500; font-family:\"Bahnschrift Condensed\",\"Bahnschrift\",\"Roboto Condensed\",\"Arial Narrow\",sans-serif; font-stretch:condensed; font-variant-numeric:tabular-nums; }\n\n@media (max-width:650px) {\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-trend-status { padding:14px 12px; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-head { flex-direction:column; gap:4px; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-source { text-align:left; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-lead { grid-template-columns:1fr; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-direction { padding:16px 0; border-right:0; border-bottom:1px solid #e7edf4; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-safety { padding:16px 0; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-direction > strong { font-size:26px; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-direction > b { font-size:20px; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-stats { grid-template-columns:1fr; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-stats > div { padding:12px 0; border-left:0 !important; border-bottom:1px solid #e7edf4; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-stats > div:last-child { border-bottom:0; padding-bottom:2px; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-status-stats strong { font-size:22px; }\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-chart-head {\n    display:flex;\n    justify-content:space-between;\n    align-items:flex-start;\n    gap:12px;\n    margin-bottom:7px;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-chart-title {\n    color:#173f73;\n    font-size:12px;\n    line-height:1.25;\n    font-weight:750;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-chart-stats {\n    color:#7f8e9c;\n    font-size:10px;\n    line-height:1.3;\n    text-align:right;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-chart-svg {\n    display:block;\n    width:100%;\n    height:auto;\n    min-height:170px;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-chart-empty {\n    min-height:150px;\n    display:flex;\n    align-items:center;\n    justify-content:center;\n    text-align:center;\n    color:#98a6b4;\n    font-size:11px;\n    line-height:1.45;\n    padding:20px;\n}\n\n\/* =========================================================\n   DUBROV\u010cAK \u00b7 DETALJNI VODOSTAJ \u2013 uredni\u010dki raspored (v0.15.0)\n   Jedna jasna hijerarhija: postaja \u2192 trenutna razina (heroj) \u2192 udaljenost do praga\n   \u2192 sekundarni pokazatelji u mre\u017ei s tankim razdjelnicima (bez kutija) \u2192 presjek.\n   ========================================================= *\/\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-head { display:flex; justify-content:space-between; align-items:flex-end; gap:16px 24px; flex-wrap:wrap; padding-bottom:18px; border-bottom:2px solid #0b3d78; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-eyebrow { color:#6f8398; font-size:11px; font-weight:700; letter-spacing:.14em; text-transform:uppercase; margin-bottom:6px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-title { margin:0; color:#0b3d78; font-size:34px; line-height:1; font-weight:800; letter-spacing:-.02em; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-title span { display:inline-block; margin-left:10px; color:#6f8398; font-size:17px; font-weight:500; letter-spacing:0; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-headside { display:flex; align-items:center; gap:18px; flex-wrap:wrap; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-status .mv-water-status { margin:0; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-clock { display:flex; flex-direction:column; align-items:flex-end; gap:2px; padding-left:18px; border-left:1px solid #dfe7ef; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-clock span { color:#8293a3; font-size:10.5px; font-weight:700; letter-spacing:.1em; text-transform:uppercase; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-clock strong { color:#0b3d78; font-size:22px; font-weight:600; font-variant-numeric:tabular-nums; font-family:\"Bahnschrift Condensed\",\"Bahnschrift\",\"Roboto Condensed\",\"Arial Narrow\",sans-serif; font-stretch:condensed; }\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-hero { display:grid; grid-template-columns:minmax(0,5fr) minmax(0,7fr); gap:0; margin-top:4px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-main { padding:24px 32px 24px 0; border-right:1px solid #e3eaf1; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-label { color:#6f8398; font-size:11px; font-weight:700; letter-spacing:.12em; text-transform:uppercase; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-levelrow { display:flex; align-items:center; justify-content:space-between; gap:16px; margin-top:8px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-level { color:#0b3d78; font-size:92px; line-height:.86; font-weight:500; letter-spacing:-.01em; font-family:\"Bahnschrift Condensed\",\"Bahnschrift\",\"Roboto Condensed\",\"Arial Narrow\",sans-serif; font-stretch:condensed; font-variant-numeric:tabular-nums; white-space:nowrap; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-level small { margin-left:6px; font-size:26px; color:#5b6f82; font-weight:500; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-arrow { display:none; flex:0 0 60px; width:60px; height:60px; align-items:center; justify-content:center; background:#eef2f6; color:#71849a; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-arrow.is-visible { display:inline-flex; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-arrow.is-up { background:#fdeedf; color:#d96e16; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-arrow.is-down { background:#e3eff8; color:#2678ad; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-arrow svg { width:34px; height:34px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-trend { display:flex; align-items:baseline; gap:8px; margin-top:14px; color:#5b6f82; font-size:13px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-trend strong { color:#0b3d78; font-size:18px; font-weight:700; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-trend strong.is-up { color:#d96e16; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-trend strong.is-down { color:#2678ad; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-gauge { margin-top:18px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-gauge .mv-gauge { margin-top:0; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-meta { display:flex; justify-content:space-between; align-items:baseline; gap:12px; margin-top:18px; padding-top:14px; border-top:1px solid #e7edf4; color:#6f8398; font-size:12px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-meta strong { color:#16385f; font-size:13px; font-weight:700; text-align:right; }\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-metrics { display:grid; grid-template-columns:repeat(3,minmax(0,1fr)); align-content:center; padding-left:32px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-metric { display:flex; flex-direction:column; gap:8px; padding:22px 18px 22px 0; border-bottom:1px solid #e7edf4; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-metric:nth-child(n+4) { border-bottom:0; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-metric:not(:nth-child(3n+1)) { padding-left:18px; border-left:1px solid #e7edf4; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-metric > span { color:#6f8398; font-size:11px; font-weight:700; letter-spacing:.08em; text-transform:uppercase; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-metric > strong { color:#0b3d78; font-size:34px; line-height:1; font-weight:500; font-family:\"Bahnschrift Condensed\",\"Bahnschrift\",\"Roboto Condensed\",\"Arial Narrow\",sans-serif; font-stretch:condensed; font-variant-numeric:tabular-nums; white-space:nowrap; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-metric > strong.is-up { color:#d96e16; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-metric > strong.is-down { color:#2678ad; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-metric-note p { margin:0; color:#6f8398; font-size:12px; line-height:1.45; }\n\n@media (max-width:1100px) {\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-hero { grid-template-columns:1fr; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-main { padding:22px 0; border-right:0; border-bottom:1px solid #e3eaf1; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-metrics { padding-left:0; }\n}\n@media (max-width:650px) {\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-title { font-size:28px; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-title span { display:block; margin:6px 0 0; font-size:15px; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-headside { width:100%; justify-content:space-between; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-clock { padding-left:0; border-left:0; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-level { font-size:76px; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-arrow { flex-basis:52px; width:52px; height:52px; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-metrics { grid-template-columns:repeat(2,minmax(0,1fr)); }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-metric { padding:16px 12px 16px 0; border-bottom:1px solid #e7edf4 !important; border-left:0 !important; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-metric:nth-child(2n) { padding-left:14px !important; border-left:1px solid #e7edf4 !important; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-metric:nth-child(2n+1) { padding-left:0 !important; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-metric:nth-last-child(-n+2) { border-bottom:0 !important; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dubx-metric > strong { font-size:24px; white-space:normal; overflow-wrap:anywhere; }\n}\n\n\/* Detaljni grafikoni Dubrov\u010dak: pragovi obrane od poplava (isprekidano, boja po stanju \u2013\n   iste boje kao legenda presjeka korita) i dnevni raspon (sjena) na 30-dnevnom grafu. *\/\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-charts > .mv-range-wrap { justify-self:start; max-width:100%; }\n@media (max-width:650px) {\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-charts > .mv-range-wrap { justify-self:stretch; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-charts .mv-range { display:flex; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-charts .mv-range button { flex:1 1 0; padding:7px 4px; font-size:11.5px; }\n}\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-chart-threshold {\n    stroke-width:1.4;\n    stroke-dasharray:5 4;\n    opacity:.85;\n    vector-effect:non-scaling-stroke;\n}\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-chart-band {\n    fill:#2e74bd;\n    opacity:.14;\n    stroke:none;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-help {\n    margin-top:14px;\n    padding-top:13px;\n    border-top:1px solid #e8eef4;\n}\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-help summary {\n    display:inline-flex;\n    align-items:center;\n    gap:8px;\n    color:#164782;\n    font-size:13px;\n    font-weight:700;\n    cursor:pointer;\n    list-style:none;\n}\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-help summary::-webkit-details-marker { display:none; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-help summary::before {\n    content:'i';\n    display:inline-flex;\n    align-items:center;\n    justify-content:center;\n    width:18px;\n    height:18px;\n    border:1.5px solid #164782;\n    font-size:11px;\n    font-weight:800;\n    font-style:normal;\n    line-height:1;\n}\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-help[open] summary::before { background:#164782; color:#fff; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-help ul {\n    margin:10px 0 0;\n    padding-left:18px;\n    color:#50677e;\n    font-size:12.5px;\n    line-height:1.55;\n}\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-help li + li { margin-top:5px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-help .mv-source-note { margin-top:10px; }\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-detail-footer {\n    margin-top:12px;\n    color:#8293a3;\n    font-size:10px;\n    line-height:1.5;\n}\n\n@media (max-width:900px) {\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-kpis {\n        grid-template-columns:repeat(2,minmax(0,1fr));\n    }\n}\n\n@media (max-width:650px) {\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-dubrovacak-detail,\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-dubrovacak-charts {\n        padding:18px 14px;\n    }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-detail-head {\n        flex-direction:column;\n        align-items:stretch;\n        gap:12px;\n    }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-clockbox {\n        min-width:0;\n        text-align:left;\n    }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-kpis {\n        grid-template-columns:1fr 1fr;\n        gap:8px;\n    }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-rates {\n        grid-template-columns:repeat(2,minmax(0,1fr));\n        gap:6px;\n        margin-top:-8px;\n    }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-rate {\n        padding:10px 8px;\n        text-align:center;\n    }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-rate-label {\n        min-height:24px;\n        font-size:8px;\n        letter-spacing:.025em;\n    }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-rate-value {\n        font-size:17px;\n        white-space:nowrap;\n    }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-rate-note {\n        text-align:left;\n        font-size:9px;\n    }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-kpi {\n        padding:11px 12px;\n    }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-kpi-value,\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-kpi-value.is-main {\n        font-size:19px;\n    }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-section-head {\n        align-items:flex-start;\n        flex-direction:column;\n        gap:3px;\n    }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-section-note {\n        text-align:left;\n    }\n    \/* Mobile: 50% ve\u0107i tekst u shematskom presjeku korita. *\/\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-section-title {\n        font-size:16.5px;\n        line-height:1.25;\n    }\n    \/* Veli\u010dine teksta presjeka na mobitelu sada postavlja crta\u010d (crossFs) u SVG jedinicama;\n       fiksni min-height je uklonjen jer je ispod presjeka ostavljao praznu plohu. *\/\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-cross-svg {\n        min-height:0;\n    }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-chart-svg {\n        min-height:150px;\n    }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-24h-summary {\n        gap:6px;\n    }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-24h-summary-item {\n        padding:9px 7px;\n        text-align:center;\n    }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-24h-summary-label {\n        font-size:7.5px;\n        letter-spacing:.025em;\n    }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-24h-summary-value {\n        font-size:17px;\n    }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-24h-summary-time {\n        font-size:7.5px;\n    }\n}\n\n@media (max-width:380px) {\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-rates {\n        grid-template-columns:1fr;\n    }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-rate {\n        display:flex;\n        align-items:center;\n        justify-content:space-between;\n        gap:10px;\n        text-align:left;\n    }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-rate-label {\n        min-height:0;\n    }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dub-rate-value {\n        margin-top:0;\n    }\n}\n\n@media (max-width:650px) {\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-level-value {\n        font-size:54px;\n    }\n\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-level-unit {\n        font-size:16px;\n        padding-bottom:5px;\n    }\n}\n        \n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warning-list { display:grid; gap:12px; width:100%; margin-top:16px;}\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warning-item { width:100%; border:1px solid #e4eaf0; padding:16px; text-align:left; background:#fff; border-radius:16px; box-shadow:0 2px 8px rgba(0,0,0,0.02);}\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warning-item.yellow { border-left:6px solid #e4b600; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warning-item.orange { border-left:6px solid #ef7d00; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warning-item.red { border-left:6px solid #cf2027; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warning-head { display:flex; justify-content:space-between; gap:12px; align-items:flex-start; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warning-level { font-size:12px; font-weight:700; letter-spacing:.02em; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warning-event { font-size:16px; font-weight:600; color:#173f73; margin-top:3px; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warning-time { font-size:12px; color:#667b8f; margin-top:6px; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warning-desc { font-size:13px; color:#405970; margin-top:8px; line-height:1.5; }\n\n        \/* Slu\u017ebena preporuka iz DHMZ CAP polja <instruction> *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warning-advice {\n            width:100%;\n            margin-top:18px;\n            padding:16px 18px;\n            background:#f3f7fb;\n            border:1px solid #dbe7f2;\n            border-radius:16px;\n            text-align:left;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warning-advice[hidden] { display:none !important; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warning-advice-title {\n            margin-bottom:7px;\n            color:#0d4f91;\n            font-size:11px;\n            font-weight:700;\n            letter-spacing:.10em;\n            text-transform:uppercase;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warning-advice-text {\n            color:#405970;\n            font-size:13px;\n            line-height:1.55;\n        }\n\n\n        \/* WMO \/ MeteoAlarm stil upozorenja: univerzalni trokut + boja ozbiljnosti. *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warning-symbol {\n            width:104px;\n            height:92px;\n            display:flex;\n            align-items:center;\n            justify-content:center;\n            color:#94a3b8;\n            --mv-warning-mark:#ffffff;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warning-symbol svg { width:100%; height:100%; display:block; overflow:visible; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warning-symbol.is-yellow { color:#f2c500; --mv-warning-mark:#1f2937; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warning-symbol.is-orange { color:#f28c00; --mv-warning-mark:#1f2937; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warning-symbol.is-red { color:#d32f2f; --mv-warning-mark:#ffffff; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warning-symbol.is-unavailable { color:#94a3b8; --mv-warning-mark:#ffffff; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warning-symbol.is-clear {\n            width:96px;\n            height:96px;\n            border-radius:50%;\n            border:4px solid #58be7b;\n            background:#f1fbf5;\n            color:#2eab60;\n            --mv-warning-mark:#2eab60;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warning-symbol.is-clear svg { width:56%; height:56%; }\n\n        \/* DHMZ radar ispod upozorenja *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-radar {\n            width:100%;\n            margin-top:26px;\n            padding-top:22px;\n            border-top:1px solid #e5edf4;\n            text-align:left;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-radar-head {\n            display:flex;\n            align-items:flex-end;\n            justify-content:space-between;\n            gap:12px;\n            margin-bottom:10px;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-radar-title {\n            color:#0d4f91;\n            font-size:12px;\n            font-weight:700;\n            letter-spacing:.09em;\n            text-transform:uppercase;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-radar-meta {\n            color:#8aa0b6;\n            font-size:10px;\n            line-height:1.35;\n            text-align:right;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-radar-frame {\n            position:relative;\n            width:100%;\n            aspect-ratio:1\/1;\n            overflow:hidden;\n            border:1px solid #dce6ef;\n            border-radius:16px;\n            background:#eef3f7;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-radar-frame img {\n            display:block;\n            width:100%;\n            height:100%;\n            object-fit:contain;\n            background:#eef3f7;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-radar-badge {\n            position:absolute;\n            left:10px;\n            bottom:10px;\n            z-index:2;\n            padding:5px 8px;\n            border-radius:999px;\n            background:rgba(15,23,42,.78);\n            color:#fff;\n            font-size:10px;\n            font-weight:600;\n            backdrop-filter:blur(6px);\n            -webkit-backdrop-filter:blur(6px);\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-radar-controls {\n            display:flex;\n            align-items:center;\n            justify-content:space-between;\n            gap:12px;\n            margin-top:9px;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-radar-play {\n            appearance:none;\n            border:1px solid #d5e1ec;\n            border-radius:999px;\n            padding:7px 11px;\n            background:#fff;\n            color:#0d4f91;\n            font:600 11px\/1 inherit;\n            cursor:pointer;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-radar-link {\n            color:#2563eb;\n            font-size:11px;\n            font-weight:600;\n            text-decoration:none;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-radar-note {\n            margin-top:7px;\n            color:#8aa0b6;\n            font-size:10px;\n            line-height:1.4;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-pill {\n            display:inline-flex;\n            align-items:center;\n            gap:6px;\n            min-height:28px;\n            padding:0 12px;\n            border-radius:999px;\n            background:#e6f5ec;\n            color:#187248;\n            font-size:12px;\n            font-weight:600;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-pill.warn { background:#fff1d9; color:#8d5b00; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-pill.danger { background:#fee2e2; color:#9f1c1c; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-pill.neutral { background:#edf3f8; color:#46657f; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-pill.good { background:#e3f5e8; color:#1f7a3d; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-pill.severe { background:#9f1c1c; color:#fff; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-pill.best { background:#0f6b3a; color:#fff; }\n\n        \/* Generi\u010dka traka razina (dijeli izgled s trakom pragova Save i peludi): kru\u017ei\u0107\/marker\n           na trenuta\u010dnoj vrijednosti, obojene zone, kva\u010dice na granicama zona. Koristi je i\n           Kvaliteta zraka (po one\u010di\u0161\u0107iva\u010du) i Vjetar (Beaufortova ljestvica). *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-scale-gauge { margin-top:8px; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-scale-gauge-track { position:relative; height:8px; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-scale-gauge-tick { position:absolute; top:0; bottom:0; width:2px; margin-left:-1px; background:#fff; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-scale-gauge-marker { position:absolute; top:50%; width:12px; height:12px; box-sizing:border-box; margin:-6px 0 0 -6px; background:#fff; border:3px solid #16385f; box-shadow:0 1px 3px rgba(0,0,0,.3); }\n\n        \/* Kvaliteta zraka: redak po one\u010di\u0161\u0107iva\u010du (isti jezik kao redak peludi). *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-aqi-row { padding:9px 0; border-bottom:1px solid #edf2f6; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-aqi-row:last-child { border-bottom:0; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-aqi-row-head { display:flex; align-items:baseline; justify-content:space-between; gap:8px; flex-wrap:wrap; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-aqi-row-name { font-size:13px; font-weight:600; color:#33475a; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-aqi-row-value { font-size:13.5px; font-weight:700; color:#16385f; white-space:nowrap; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-aqi-row-name em { font-style:normal; font-weight:400; color:#6f8398; margin-left:4px; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-aqi-row-hint { margin-top:3px; font-size:12px; line-height:1.4; color:#6f8398; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-help .mv-aqi-help-h { margin:14px 0 4px; font-size:12px; font-weight:700; letter-spacing:.08em; text-transform:uppercase; color:#16385f; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-aqi-row-scale { display:flex; align-items:center; gap:10px; margin-top:6px; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-aqi-row-scale .mv-scale-gauge { flex:1 1 auto; min-width:0; margin-top:0; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-aqi-row-scale .mv-pill { flex:0 0 auto; }\n\n        \/* Lokalni izbor naselja za CAMS blokove. Koristi isklju\u010divo postoje\u0107u\n           MV tipografiju i ravne kontrole; ne utje\u010de na kartu ni druge kartice. *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-air-place-control { margin:0 0 15px; padding:0 0 13px; border-bottom:1px solid #edf2f6; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-air-place-control label { display:block; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-air-place-label { display:block; margin:0 0 6px; font-size:11px; font-weight:700; letter-spacing:.08em; text-transform:uppercase; color:#6f8398; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-air-place-select { display:block; width:100%; min-height:38px; box-sizing:border-box; padding:7px 32px 7px 10px; border:1px solid #dbe4ec; border-radius:0; background:#fff; color:#16385f; font:inherit; font-size:13px; font-weight:600; line-height:1.35; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-air-place-select:focus { outline:2px solid rgba(20,90,165,.18); outline-offset:1px; border-color:#8aaac8; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-air-place-select:disabled { opacity:.62; cursor:wait; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-air-place-meta { margin-top:6px; font-size:11.5px; line-height:1.4; color:#6f8398; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-air-place-meta strong { color:#33475a; font-weight:600; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-air-place-meta.is-error { color:#9f1c1c; }\n\n        \/* Vjetar: traka ja\u010dine 0\u201312 Bf s naslovom trenuta\u010dne kategorije. *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-beaufort-scale { margin-top:16px; padding-top:14px; border-top:1px solid #e7edf4; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-beaufort-caption { display:flex; align-items:baseline; justify-content:space-between; gap:8px; margin-top:9px; color:#5b6f82; font-size:12.5px; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-beaufort-caption strong { color:#16385f; font-size:13.5px; }\n\n        \/* Oborine: isti MV vizualni jezik, uz funkcionalne raspona 7d \/ 30d \/ 12m. *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-rain .mv-gauge-legend { margin-top:14px; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-rain-head { display:flex; align-items:center; justify-content:space-between; gap:10px 14px; flex-wrap:wrap; margin-bottom:10px; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-rain-head .mv-card-title { margin:0; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-rain-sub { font-weight:inherit; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-rain-range button { padding:6px 11px; font-size:12px; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-rain-svg { padding-top:6px; border-bottom:1px solid #edf2f6; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-rain-svg svg { display:block; width:100%; height:auto; overflow:visible; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-rain-svg[hidden], #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-chart[hidden] { display:none; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-rain-note { margin:6px 0 2px; font-size:12px; line-height:1.4; color:#6f8398; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-rain-delta.is-wet { color:#1f5c96; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-rain-delta.is-dry { color:#b45309; }\n\n        \/* Pelud: sa\u017eetak, redak po vrsti i mini traka razine (isti vizualni jezik kao traka pragova Save). *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-pollen-summary { margin:0 0 14px; font-size:13px; line-height:1.4; color:#4d6178; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-pollen-summary strong { color:#16385f; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-pollen-row { padding:10px 0; border-bottom:1px solid #edf2f6; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-pollen-row:last-child { border-bottom:0; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-pollen-head { display:flex; align-items:baseline; justify-content:space-between; gap:8px; flex-wrap:wrap; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-pollen-name { display:flex; align-items:center; gap:7px; font-size:13.5px; font-weight:600; color:#33475a; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-pollen-value { font-size:14px; font-weight:700; color:#16385f; white-space:nowrap; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-pollen-value small { font-weight:600; color:#6b7f93; font-size:11px; margin-left:2px; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-pollen-row-hint { margin-top:3px; font-size:12px; line-height:1.4; color:#6f8398; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-pollen-scale { display:flex; align-items:center; gap:10px; margin-top:9px; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-pollen-gauge { flex:1 1 auto; min-width:0; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-pollen-gauge-track { position:relative; height:8px; background:#eef1f4; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-pollen-gauge-tick { position:absolute; top:0; bottom:0; width:2px; margin-left:-1px; background:#fff; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-pollen-gauge-marker { position:absolute; top:50%; width:12px; height:12px; box-sizing:border-box; margin:-6px 0 0 -6px; background:#fff; border:3px solid #16385f; box-shadow:0 1px 3px rgba(0,0,0,.3); }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-pollen-scale .mv-pill { flex:0 0 auto; }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-aqi {\n            display:flex;\n            align-items:center;\n            gap:16px;\n            margin-bottom:16px;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-face {\n            width:80px;\n            height:80px;\n            border-radius:50%;\n            display:flex;\n            align-items:center;\n            justify-content:center;\n            border:4px solid #29a75b;\n            color:#29a75b;\n            font-size:42px;\n            background:#f0fbf5;\n        }\n        \n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-face svg { width:1em; height:1em; }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-aqi-number {\n            font-size:48px;\n            line-height:1;\n            font-weight:600;\n            color:#173f73;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-aqi-label {\n            margin-top:8px;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dot {\n            width:12px;\n            height:12px;\n            border-radius:50%;\n            display:inline-block;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-uv-wrap {\n            display:grid;\n            grid-template-columns:auto 1fr;\n            gap:16px;\n            align-items:center;\n            margin-bottom:16px;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-uv-number {\n            font-size:64px;\n            line-height:1;\n            font-weight:600;\n            color:#ee8a00;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-uv-scale {\n            margin-top:16px;\n            display:grid;\n            grid-template-columns:repeat(11, 1fr) auto;\n            gap:4px;\n            align-items:end;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-uv-bar {\n            height:10px;\n            border-radius:4px;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-uv-labels {\n            display:grid;\n            grid-template-columns:repeat(11, 1fr) auto;\n            gap:4px;\n            margin-top:6px;\n            font-size:11px;\n            color:#1d3252;\n            text-align:center;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-chart {\n            height:170px;\n            display:flex;\n            align-items:flex-end;\n            gap:18px;\n            padding:10px 4px 0;\n            border-bottom:1px solid #edf2f6;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-bar-col {\n            flex:1 1 0;\n            min-width:0;\n            text-align:center;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-bar-value {\n            font-size:12px;\n            color:#1b4b87;\n            font-weight:600;\n            margin-bottom:6px;\n            min-height:18px;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-bar {\n            width:100%;\n            max-width:34px;\n            margin:0 auto;\n            border-radius:8px 8px 0 0;\n            background:linear-gradient(180deg, #2c8cff 0%, #5ba8ff 100%);\n            min-height:4px;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-bar-label {\n            font-size:12px;\n            color:#53697f;\n            margin-top:8px;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wind-wrap {\n            display:grid;\n            grid-template-columns:170px 1fr;\n            gap:24px;\n            align-items:center;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wind-svg {\n            width:160px;\n            height:160px;\n            display:block;\n            margin:auto;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-ok-box {\n            display:grid;\n            justify-items:center;\n            gap:12px;\n            padding-top:10px;\n            text-align:center;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-ok-circle {\n            width:104px;\n            height:104px;\n            border-radius:50%;\n            display:flex;\n            align-items:center;\n            justify-content:center;\n            border:4px solid #6fd28f;\n            color:#2eab60;\n            font-size:54px;\n            background:#f1fbf5;\n        }\n        \n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-ok-circle svg { width:1em; height:1em; }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-climate-grid {\n            display:grid;\n            grid-template-columns:repeat(2, minmax(0, 1fr));\n            gap:16px 24px;\n            font-size:14px;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-climate-item {\n            display:flex;\n            justify-content:space-between;\n            gap:12px;\n            padding:6px 0;\n            border-bottom: 1px solid #f1f5f9;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-source-note {\n            margin-top:16px;\n            color:#94a3b8;\n            font-size:11px;\n            line-height:1.4;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-ref {\n            display:none;\n            margin:10px 0 16px;\n            padding:15px 18px;\n            border:1px solid #d9e4ee;\n            border-radius:16px;\n            background:#f7fafc;\n            color:#405970;\n            font-size:15px;\n            line-height:1.4;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-ref.is-visible {\n            display:block;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-ref strong {\n            color:#0b3d78;\n            font-size:17px;\n            font-weight:700;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-ref-meta {\n            margin-top:4px;\n            color:#7d8d9c;\n            font-size:12px;\n            line-height:1.4;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-ref-grid {\n            display:grid;\n            grid-template-columns:repeat(2,minmax(0,1fr));\n            gap:0 18px;\n            margin-top:12px;\n            border-top:1px solid #e3ebf2;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-ref-row {\n            display:none;\n            align-items:center;\n            justify-content:space-between;\n            gap:10px;\n            min-width:0;\n            padding:9px 0;\n            border-bottom:1px solid #e8eef4;\n            color:#4b6277;\n            font-size:13px;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-ref-row.is-visible { display:flex; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-ref-row span:last-child {\n            color:#0b3d78;\n            font-weight:700;\n            white-space:nowrap;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-ref-note {\n            display:none;\n            margin-top:7px;\n            color:#8b99a7;\n            font-size:10.5px;\n            line-height:1.35;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-ref-note.is-visible { display:block; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-ref-temp { color:#0b3d78; font-weight:700; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-ref-at {\n            display:inline-block;\n            margin-left:4px;\n            padding:1px 7px;\n            border:1px solid #cfdbe6;\n            background:#fff;\n            color:#405970;\n            font-size:12px;\n            font-weight:700;\n            font-variant-numeric:tabular-nums;\n            letter-spacing:.02em;\n            vertical-align:2px;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-ref-at:empty { display:none; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-ref-meta b { color:#405970; font-weight:700; font-variant-numeric:tabular-nums; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-ref-stale {\n            display:none;\n            margin-top:6px;\n            padding-left:8px;\n            border-left:2px solid #e8a33d;\n            color:#8a5a14;\n            font-size:12px;\n            line-height:1.4;\n        }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-ref.is-stale .mv-dhmz-ref-stale { display:block; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-ref.is-stale .mv-dhmz-ref-temp,\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-ref.is-stale .mv-dhmz-ref-row span:last-child { color:#7d8d9c; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-ref.is-stale .mv-dhmz-ref-at { border-color:#e8a33d; color:#8a5a14; background:#fff8ec; }\n\n        @media (max-width:650px) {\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-ref-grid { grid-template-columns:1fr; }\n        }\n\n        @media (max-width:1100px) {\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap { grid-template-columns:repeat(3,minmax(0,1fr)); }\n        }\n        @media (max-width:700px) {\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap,\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap.mv-water-secondary { grid-template-columns:1fr; }\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-footer {\n            margin:0 14px 24px;\n            padding:16px 24px;\n            border-radius:24px;\n            background:#ffffff;\n            color:#64748b;\n            display:flex;\n            gap:16px;\n            justify-content:space-between;\n            flex-wrap:wrap;\n            font-size:13px;\n            border:1px solid var(--mv-line);\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-place-label {\n            background:transparent;\n            border:0;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-place-label-inner {\n            --mv-dx:0px;\n            --mv-dy:0px;\n            transform:translate(calc(-50% + var(--mv-dx)), calc(-50% + var(--mv-dy)));\n            color:#fff;\n            font-size:13px;\n            font-weight:600;\n            white-space:nowrap;\n            text-shadow:0 2px 4px rgba(0,0,0,.8), 0 0 10px rgba(0,0,0,.6);\n            pointer-events:none;\n            text-align:center;\n        }\n\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-leaflet-attribution {\n            background:rgba(255,255,255,.85);\n            border-radius:12px;\n            padding:4px 8px;\n            margin-bottom:8px !important;\n            margin-right:8px !important;\n        }\n\n        @media (max-width:1100px) {\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-span-3,\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-span-4,\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-span-5 { grid-column:span 6; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-map-frame { height:500px; }\n        }\n\n        @media (max-width:820px) {\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-head { padding:16px 20px; align-items:flex-start; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-updated { display:none; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-map-frame { height:580px; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wind-wrap { grid-template-columns:1fr; }\n        }\n\n        @media (max-width:620px) {\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-crest { width:44px; max-height:56px; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-map-wrap { padding:14px 14px 0; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-map-frame { height:640px; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-side-btn,\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-side-link { min-height:44px; font-size:12px; padding:0 12px; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-grid { grid-template-columns:1fr; gap:16px; padding:16px; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-span-3,\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-span-4,\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-span-5,\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-span-12 { grid-column:1; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-now-temp { font-size:52px; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-climate-grid { grid-template-columns:1fr; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-chart { gap:10px; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-radar-controls { width:calc(100% - 32px); padding:10px 14px; bottom: 16px; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-radar-row { grid-template-columns: 36px 1fr 54px; gap:8px; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-radar-time.start,\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-radar-time.end { display:none; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-layer-menu { grid-template-columns:repeat(4,minmax(0,1fr)); }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-layer-btn,\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-layer-link { flex-direction:column; min-height:54px; font-size:10px; gap:6px; }\n        }\n\n        \/* Clean v2 styling overrides adjusted for rounded corners *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-head { align-items:flex-end; padding:4px 0 24px; border-bottom:0; background:transparent; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-crest { display:none; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-eyebrow { margin:0 0 12px; color:#111827; font-size:12px; letter-spacing:.15em; font-weight:600; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-title { color:#111827; font-size:clamp(34px,4vw,48px); font-weight:700; letter-spacing:-.03em; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-subtitle { max-width:760px; margin-top:12px; color:#4B5563; font-size:16px; line-height:1.5; font-weight:400; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-updated { color:#6B7280; font-size:12px; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-updated strong { color:#111827; font-size:13px; }\n        \n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-layer-menu-wrap { padding:0; margin:0 0 16px; background:transparent; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-map-wrap { padding:0; background:transparent; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-grid { gap:24px; padding:24px 0 0; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-footer { margin:24px 0 0; }\n        \n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-current { order:10; grid-column:span 6; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-warnings { order:11; grid-column:span 6; position:relative; overflow:hidden; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-nowcast { order:12; grid-column:span 12; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-forecast { order:13; grid-column:span 12; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-dubrovacak-detail { order:14; grid-column:span 12; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-sava { order:20; grid-column:span 12; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-odrakupa { order:30; grid-column:span 6; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-rain { order:31; grid-column:span 6; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-dubrovacak-charts { order:32; grid-column:span 12; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-air { order:50; grid-column:span 6; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-pollen { order:51; grid-column:span 6; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-uv { order:60; grid-column:span 6; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-wind { order:61; grid-column:span 6; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-climate { order:62; grid-column:span 8; }\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-soil { order:63; grid-column:span 4; }\n\n        @media (max-width:900px) {\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-current,\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-warnings,\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-odrakupa,\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-rain,\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-soil { grid-column:span 12; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-air,\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-pollen,\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-uv,\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-wind { grid-column:span 6; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-climate { grid-column:span 12; }\n            \/* Tablet zadr\u017eava raspored iz 0.18.7; novo preslagivanje vrijedi samo za PC. *\/\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-soil { order:52; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-climate { order:62; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-map-frame { height:500px; }\n        }\n        @media (max-width:650px) {\n            \/* Mobilni prikaz zadr\u017eava isti redoslijed blokova kao PC. *\/\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-current { order:10; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-warnings { order:11; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-nowcast { order:12; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-forecast { order:13; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-dubrovacak-detail { order:14; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-sava { order:20; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-odrakupa { order:30; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-rain { order:31; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-dubrovacak-charts { order:32; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-air { order:50; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-pollen { order:51; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-soil { order:52; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-uv { order:60; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-wind { order:61; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-climate { order:62; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-head { align-items:flex-start; flex-direction:column; gap:12px; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-updated { text-align:left; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-air,\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-pollen,\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-soil,\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-uv,\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-rain,\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-wind,\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-climate { grid-column:span 12; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-map-frame { height:440px; }\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card { padding:20px; }\n        }\n        \n        \/* Sljede\u0107a 3 sata \u00b7 15-minutna vremenska crta *\/\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-nowcast-head{display:flex;align-items:flex-end;justify-content:space-between;gap:14px;margin-bottom:14px}\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-nowcast-sub{color:#6b7280;font-size:12px;line-height:1.4;text-align:right}\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-nowcast-scroll{overflow-x:auto;overscroll-behavior-inline:contain;scroll-snap-type:x proximity;padding:2px 2px 10px;-webkit-overflow-scrolling:touch;scrollbar-width:thin}\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-nowcast-track{display:grid;grid-auto-flow:column;grid-auto-columns:minmax(112px,1fr);gap:8px;min-width:max-content}\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-nowcast-item{scroll-snap-align:start;min-width:112px;padding:12px 10px;border:1px solid #e5e7eb;border-radius:14px;background:#f8fafc;text-align:center}\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-nowcast-item.is-first{border-color:#bfd7ea;background:#f3f9fd;box-shadow:inset 0 0 0 1px rgba(23,105,170,.06)}\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-nowcast-time{font-size:12px;font-weight:800;color:#475569;font-variant-numeric:tabular-nums}\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-nowcast-icon{height:34px;margin:7px 0 4px;display:flex;align-items:center;justify-content:center;font-size:29px}\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-nowcast-temp{display:block;font-size:21px;line-height:1.1;font-weight:800;color:#123b5d}\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-nowcast-rain{margin-top:7px;font-size:12px;font-weight:700;color:#2678ad;white-space:nowrap}\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-nowcast-wind{margin-top:4px;font-size:11px;color:#64748b;white-space:nowrap}\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-nowcast-empty{padding:18px;border:1px dashed #d7e0e6;border-radius:14px;color:#738796;font-size:13px;text-align:center}\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-nowcast-legend{display:flex;flex-wrap:wrap;gap:10px 16px;margin-top:2px;color:#6b7280;font-size:11px}\n        #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-nowcast-legend strong{color:#475569}\n        @media (max-width:650px){\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-nowcast-head{align-items:flex-start;flex-direction:column;gap:4px}\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-nowcast-sub{text-align:left}\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-nowcast-track{grid-auto-columns:104px;gap:7px}\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-nowcast-item{min-width:104px;padding:11px 8px}\n            #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-nowcast-temp{font-size:20px}\n        }\n\n        \/* Fotografija u bloku Trenuta\u010dno vrijeme *\/\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-current {\n    display:flex;\n    flex-direction:column;\n    overflow:hidden;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-current-photo {\n    margin-top:auto;\n    margin-left:-24px;\n    margin-right:-24px;\n    margin-bottom:-24px;\n    min-height:420px;\n    overflow:hidden;\n    border-radius:0 0 24px 24px;\n}\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-current-photo img {\n    display:block;\n    width:100%;\n    height:100%;\n    min-height:420px;\n    object-fit:cover;\n    object-position:center center;\n}\n\n@media (max-width:650px) {\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-current-photo {\n        margin-left:-20px;\n        margin-right:-20px;\n        margin-bottom:-20px;\n        min-height:0;\n        aspect-ratio:16 \/ 9;\n        border-radius:0 0 24px 24px;\n    }\n\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-current-photo img {\n        min-height:0;\n        height:100%;\n    }\n}\n\n\/* Desktop: fotografija odmah ispod podataka, bez velike prazne plohe.\n   Mobilni prikaz ostaje nepromijenjen. *\/\n@media (min-width:901px) {\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-current {\n        align-self:start;\n    }\n\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-current-photo {\n        margin-top:24px;\n    }\n}\n\n\/* =========================================================\n   VODOSTAJI \u2013 uredni\u010dki raspored (v0.16.0), FT \/ \u0161vicarska tipografija:\n   jedan heroj (broj), sve ostalo podre\u0111eno; tanke linije umjesto kutija.\n   Mre\u017ea kartica crta razdjelnike kroz gap:1px na obojenoj podlozi.\n   ========================================================= *\/\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-sava .mv-sava-head,\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-odrakupa .mv-sava-head { align-items:flex-end; padding-bottom:12px; margin-bottom:14px; border-bottom:2px solid #0b3d78; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-sava-head-note { color:#6f8398; font-size:12px; }\n\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap,\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap.mv-water-secondary { gap:14px !important; background:none; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-box { border:1px solid #e3eaf1 !important; border-radius:0 !important; box-shadow:none !important; background:#fff; padding:20px 20px 22px; min-width:0; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-box.is-rise-1 { background:var(--mv-rise-bg-1,#fff8ef); border-color:var(--mv-rise-border,#efbd8d) !important; box-shadow:inset 0 4px 0 var(--mv-rise-accent,#ef7d22) !important; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-box.is-rise-2 { background:#fbf6ef; border-color:#e8d8c4 !important; box-shadow:inset 0 4px 0 #c9a57c !important; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-box.is-rise-3 { background:#f6f7f8; border-color:#dde2e7 !important; box-shadow:inset 0 4px 0 #a9b3bd !important; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-box.is-rise-3 .mv-water-rank { background:#e9ecef; color:#4d5a66; border:0; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-box.is-rise-3 .mv-water-history-line { stroke:#6f7f8f; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-box.is-rise-3 .mv-water-history-area,\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-box.is-rise-3 .mv-water-history-band,\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-box.is-rise-3 .mv-water-history-dot { fill:#6f7f8f; }\n\n\/* Zaglavlje kartice: naziv + oznaka ranga u istom retku (bez rezerviranog praznog reda). *\/\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-top { flex-direction:column; align-items:flex-start; gap:6px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-name { font-size:17px; font-weight:700; color:#0b3d78; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-rank { margin:0 !important; padding:3px 8px; font-size:10.5px; letter-spacing:.04em; text-transform:uppercase; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-rank { display:inline-flex !important; min-height:20px; align-items:center; margin-top:10px !important; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-rank:not(.is-visible) { visibility:hidden; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-fresh { margin-top:4px; font-size:12px; }\n\n\/* Heroj: broj + strelica bez podloge + promjena od zadnjeg mjerenja. *\/\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-levelrow { margin-top:14px; align-items:center; }\n\/* Broj se mjeri prema \u0161irini kartice (container query), pa uvijek ostavlja mjesto\n   za stupac sa strelicom (gore) i jedinicom \"cm\" (dolje). *\/\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-box { container-type:inline-size; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-levelrow { display:flex; align-items:center; justify-content:space-between; gap:10px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-level { min-width:0; flex:1 1 auto; overflow:hidden; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-level { display:flex; align-items:baseline; gap:5px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-level-value { font-size:clamp(36px, 4.5vw, 80px) !important; font-size:clamp(36px, calc((100cqw - 84px) \/ (var(--mv-chars, 3) * 0.6)), 96px) !important; line-height:.9 !important; white-space:nowrap; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-level-unit { padding:0 !important; font-size:15px !important; font-weight:600; color:#5b6f82; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-box.is-unavailable .mv-water-arrow { display:none !important; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-arrow { display:inline-flex !important; flex-shrink:0 !important; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-arrow:not(.is-visible) { visibility:hidden; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-level-unit { font-size:17px; padding-bottom:4px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-arrow { background:none !important; flex:0 0 34px; width:34px; height:34px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-arrow svg { width:32px; height:32px; stroke-width:2.6; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-last { display:flex; align-items:center; justify-content:space-between; gap:8px; margin-top:12px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-last:empty { display:none; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-last > span { color:#6f8398; font-size:12px; white-space:nowrap; overflow:hidden; text-overflow:ellipsis; min-width:0; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-last > strong { display:inline-flex; align-items:center; gap:4px; flex:0 0 auto; font-size:14px; font-weight:700; white-space:nowrap; color:#71849a; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-last > strong svg { width:13px; height:13px; flex:0 0 13px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-last > strong.is-up { color:#d96e16; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-last > strong.is-down { color:#2678ad; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-last > strong.is-none { color:#a9b5c1; }\n\n\/* Promjene: 24 h u punom retku, 3\/7\/30 dana u tri stupca; svaki je ujedno izbornik grafa. *\/\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-changes { margin-top:16px; border-top:1px solid #0b3d78; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-main, #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-cell { appearance:none; border:0; background:none; font:inherit; color:inherit; cursor:pointer; text-align:left; width:100%; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-main { display:flex; align-items:center; justify-content:space-between; gap:10px; padding:10px 0; border-bottom:1px solid #e3eaf1; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-main > span { color:#4d6178; font-size:13px; white-space:nowrap; overflow:hidden; text-overflow:ellipsis; min-width:0; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-grid { display:grid; grid-template-columns:repeat(3,minmax(0,1fr)); border-bottom:1px solid #e3eaf1; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-cell { display:flex; flex-direction:column; gap:4px; padding:9px 0 10px 10px; border-left:1px solid #e3eaf1; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-cell:first-child { padding-left:0; border-left:0; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-cell > span { color:#6f8398; font-size:10.5px; font-weight:700; letter-spacing:.08em; text-transform:uppercase; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-main > strong, #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-cell > strong { display:inline-flex; align-items:center; gap:4px; font-weight:700; white-space:nowrap; color:#71849a; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-main > strong { font-size:15px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-cell > strong { font-size:13.5px; gap:2px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-cell > strong small { margin-left:2px; font-size:10px; font-weight:600; opacity:.8; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-cell > strong svg { width:12px !important; height:12px !important; flex-basis:12px !important; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-main > strong svg, #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-cell > strong svg { width:14px; height:14px; flex:0 0 14px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-main > strong.is-up, #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-cell > strong.is-up { color:#d96e16; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-main > strong.is-down, #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-cell > strong.is-down { color:#2678ad; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-main > strong.is-none, #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-cell > strong.is-none { color:#a9b5c1; font-weight:600; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-main.is-selected, #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-cell.is-selected { box-shadow:inset 0 -2px 0 #0b3d78; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-main.is-selected > span, #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-cell.is-selected > span { color:#0b3d78; font-weight:700; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-main:hover > span, #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-cell:hover > span { color:#0b3d78; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-main:focus-visible, #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-wc-cell:focus-visible { outline:2px solid #145aa5; outline-offset:-2px; }\n\n\/* Stanje: oznaka bez kutije (kvadrati\u0107 boje + tekst); informativni izvor kao obi\u010dan tekst. *\/\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-status-wrap { margin-top:12px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-status { padding:0; border:0; background:none !important; font-size:11px; letter-spacing:.06em; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-status-icon { width:12px; height:12px; flex:0 0 12px; border:0; background:#8fb3d2; color:transparent; font-size:0; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-status.is-warn .mv-water-status-icon { background:#e2b619; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-status.is-danger .mv-water-status-icon { background:#d24545; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-info { color:#6f8398; font-size:12px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-gauge-none { margin-top:14px; font-size:12px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-extra { font-size:12px; margin-top:8px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-history-block { border-top:1px solid #e3eaf1; }\n\n@media (max-width:1100px) {\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-sava .mv-river { border:0; padding:4px 0 14px; margin-bottom:0; background:none; }\n}\n@media (max-width:700px) {\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-box { padding:20px 4px 24px; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-water-wrap .mv-water-rank:not(.is-visible) { display:none !important; }\n    #mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-sava-head-note { width:100%; }\n}\n\n\/* Su\u010delje nikad ne smije pro\u0161iriti stranicu (na iOS-u \u0161iroki sadr\u017eaj pomi\u010de cijelu\n   stranicu ulijevo). Stavke mre\u017ee smiju se suziti, karta je zatvorena u svoj okvir. *\/\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 { max-width:100%; overflow-x:hidden; overflow-x:clip; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-grid > *,\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-grid .mv-card > * { min-width:0; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-map-frame { contain:layout paint; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mvmeteo-map-frame .leaflet-container { overflow:hidden !important; max-width:100%; }\n\n\/* ===== Trenuta\u010dno vrijeme (v0.18.0) ===== *\/\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-now-icon { font-size:76px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-now-unit { margin-left:4px; font-size:.45em; font-weight:600; color:#5b6f82; vertical-align:top; position:relative; top:.25em; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-now-desc { margin:6px 0 2px; color:#16385f; font-size:15px; font-weight:600; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-now-desc:empty { display:none; }\n\n\/* ===== Upozorenja DHMZ (v0.18.0): zaglavlje u jednom retku, bez praznog prostora ===== *\/\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-warnings { display:flex; flex-direction:column; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-warnings .mv-ok-box { flex:1 1 auto; display:flex; flex-direction:column; align-items:stretch; text-align:left !important; padding:0 !important; min-height:0 !important; background:none !important; border:0 !important; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warn-head { display:flex; align-items:center; gap:16px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warn-head .mv-warning-symbol { flex:0 0 52px; width:52px !important; height:52px !important; margin:0 !important; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warn-headtext { min-width:0; }\n\/* Radar ispunjava preostalu visinu kartice (nema praznog prostora ispod). *\/\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-warnings .mv-dhmz-radar { flex:1 1 auto; display:flex; flex-direction:column; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-warnings .mv-dhmz-radar-frame { flex:1 1 auto; min-height:240px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warn-title { font-size:18px; font-weight:800; letter-spacing:.01em; line-height:1.2; color:#1e293b; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warn-text { margin-top:3px; color:#5b6f82; font-size:13px; line-height:1.4; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-warnings .mv-warning-list:not(:empty) { margin-top:16px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-warnings .mv-warning-list:empty { display:none; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-warnings .mv-warning-item { border:0 !important; border-left:4px solid #f2c500 !important; border-radius:0 !important; background:#fffbea !important; padding:10px 12px !important; margin:0 0 8px !important; text-align:left; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-warnings .mv-warning-item.orange { border-left-color:#f28c00 !important; background:#fff4e8 !important; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-warnings .mv-warning-item.red { border-left-color:#d32f2f !important; background:#fdecec !important; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-warnings .mv-warning-advice:not([hidden]) { margin-top:8px; padding:10px 12px; border-left:4px solid #94a3b8; background:#f6f8fa; text-align:left; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warn-meta { display:flex; justify-content:space-between; align-items:baseline; gap:12px; flex-wrap:wrap; margin-top:14px; padding-top:12px; border-top:1px solid #e7edf4; color:#8293a3; font-size:12px; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-warn-meta a { color:#145aa5; font-weight:700; text-decoration:none; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-warnings .mv-dhmz-radar { margin-top:18px !important; padding-top:16px !important; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-card-warnings .mv-dhmz-radar-frame { aspect-ratio:9 \/ 7; border-radius:0 !important; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-radar-layer { position:absolute; inset:0; width:100% !important; height:100% !important; object-fit:contain; opacity:0; transition:opacity .28s ease; }\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 .mv-dhmz-radar-layer.is-on { opacity:1; }\n\n\/* Ravni rubovi samo na HTML plohama Meteo su\u010delja. SVG shematskog\n   presjeka korita, uklju\u010duju\u0107i zaobljenu plavu plohu, ostaje netaknut. *\/\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72,\n#mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72 :is(div, section, article, button, a, span, img, input, label, li, ul, ol, p, header, footer) {\n    border-radius:0 !important;\n}\n        \n    <\/style>\n\n    <div class=\"mvmeteo-head\">\n        <div class=\"mvmeteo-brand\">\n            <img decoding=\"async\" class=\"mvmeteo-crest\" src=\"https:\/\/digitalna.hr\/wp-content\/plugins\/mv-meteo-dashboard\/assets\/grb-martinska-ves.png\" alt=\"Grb Op\u0107ine Martinska Ves\">\n            <div>\n                <div class=\"mvmeteo-eyebrow\">OP\u0106INA MARTINSKA VES<\/div>\n                <h2 class=\"mvmeteo-title\">Meteo Martinska Ves<\/h2>\n                <div class=\"mvmeteo-subtitle\">Vrijeme, kvaliteta zraka, vodostaji i slu\u017ebena DHMZ upozorenja na jednom mjestu.<\/div>\n            <\/div>\n        <\/div>\n\n        <div class=\"mvmeteo-updated\">\n            A\u017dURIRANO: <strong data-role=\"updated\">\u2014<\/strong> \u27f3\n        <\/div>\n    <\/div>\n\n    <div class=\"mvmeteo-layer-menu-wrap\">\n        <nav class=\"mvmeteo-layer-menu\" aria-label=\"Meteorolo\u0161ki slojevi i izvori\">\n            <button type=\"button\" class=\"mvmeteo-layer-btn is-active\" data-mapmode=\"temperature\">\n                <span class=\"mvmeteo-layer-icon\"><svg viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><path d=\"M14 14.76V3.5a2.5 2.5 0 0 0-5 0v11.26a4.5 4.5 0 1 0 5 0z\"><\/path><\/svg><\/span><span>Temperatura<\/span>\n            <\/button>\n            <button type=\"button\" class=\"mvmeteo-layer-btn\" data-mapmode=\"wind\">\n                <span class=\"mvmeteo-layer-icon\"><svg viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><path d=\"M9.59 4.59A2 2 0 1 1 11 8H2m10.59 11.41A2 2 0 1 0 14 16H2m15.73-8.27A2.5 2.5 0 1 1 19.5 12H2\"><\/path><\/svg><\/span><span>Vjetar<\/span>\n            <\/button>\n            <button type=\"button\" class=\"mvmeteo-layer-btn\" data-mapmode=\"rain\">\n                <span class=\"mvmeteo-layer-icon\"><svg viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><path d=\"M16 13v8\"><\/path><path d=\"M8 13v8\"><\/path><path d=\"M12 15v8\"><\/path><path d=\"M20 16.58A5 5 0 0 0 18 7h-1.26A8 8 0 1 0 4 15.25\"><\/path><\/svg><\/span><span>Oborine<\/span>\n            <\/button>\n            <a class=\"mvmeteo-layer-link\" href=\"https:\/\/www.sat24.com\/en-gb\/country\/hr\" target=\"_blank\" rel=\"noopener noreferrer\">\n                <span class=\"mvmeteo-layer-icon\"><svg viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><path d=\"M12 2a10 10 0 1 0 10 10H12V2Z\"><\/path><path d=\"M21.18 8.02c-1-2.3-2.85-4.17-5.16-5.18\"><\/path><\/svg><\/span><span>Satelit<\/span>\n            <\/a>\n        <\/nav>\n    <\/div>\n\n    <div class=\"mvmeteo-map-wrap\">\n        <div class=\"mvmeteo-map-frame\">\n            <div class=\"mvmeteo-map\" data-role=\"map\" aria-label=\"Meteorolo\u0161ka karta Op\u0107ine Martinska Ves\"><\/div>\n            \n        <\/div>\n    <\/div>\n\n    <div class=\"mvmeteo-grid\">\n\n        <section class=\"mv-card mv-span-3 mv-card-current\">\n            <h3 class=\"mv-card-title\">Trenuta\u010dno vrijeme<\/h3>\n            <div class=\"mv-now\">\n                <div class=\"mv-now-icon\" data-role=\"now-icon\"><svg viewBox=\"0 0 24 24\" width=\"1em\" height=\"1em\" stroke=\"currentColor\" stroke-width=\"2\" fill=\"none\" stroke-linecap=\"round\" stroke-linejoin=\"round\" style=\"color:#f59e0b\"><circle cx=\"12\" cy=\"12\" r=\"5\"><\/circle><\/svg><\/div>\n                <div>\n                    <div class=\"mv-now-temp\"><span data-role=\"temp\">\u2014<\/span><span class=\"mv-now-unit\">\u00b0C<\/span><\/div>\n                    <div class=\"mv-now-desc\" data-role=\"now-desc\"><\/div>\n                    <div class=\"mv-muted\">Osje\u0107a se kao <strong data-role=\"feels\">\u2014<\/strong>\u00b0C<\/div>\n                <\/div>\n            <\/div>\n\n            <div style=\"margin-top:14px\">\n                <div class=\"mv-kv\"><span class=\"mv-kv-label\"><svg viewBox=\"0 0 24 24\" width=\"16\" height=\"16\" stroke=\"currentColor\" stroke-width=\"2\" fill=\"none\" stroke-linecap=\"round\" stroke-linejoin=\"round\" style=\"color:#64748b\"><path d=\"M12 2.69l5.66 5.66a8 8 0 1 1-11.31 0z\"><\/path><\/svg> Vlaga<\/span><strong data-role=\"humidity\">\u2014<\/strong><\/div>\n                <div class=\"mv-kv\"><span class=\"mv-kv-label\"><svg viewBox=\"0 0 24 24\" width=\"16\" height=\"16\" stroke=\"currentColor\" stroke-width=\"2\" fill=\"none\" stroke-linecap=\"round\" stroke-linejoin=\"round\" style=\"color:#64748b\"><path d=\"M9.59 4.59A2 2 0 1 1 11 8H2m10.59 11.41A2 2 0 1 0 14 16H2m15.73-8.27A2.5 2.5 0 1 1 19.5 12H2\"><\/path><\/svg> Vjetar<\/span><strong data-role=\"wind\">\u2014<\/strong><\/div>\n                <div class=\"mv-kv\"><span class=\"mv-kv-label\"><svg viewBox=\"0 0 24 24\" width=\"16\" height=\"16\" stroke=\"currentColor\" stroke-width=\"2\" fill=\"none\" stroke-linecap=\"round\" stroke-linejoin=\"round\" style=\"color:#64748b\"><circle cx=\"12\" cy=\"12\" r=\"10\"><\/circle><circle cx=\"12\" cy=\"12\" r=\"4\"><\/circle><\/svg> Tlak zraka<\/span><strong data-role=\"pressure\">\u2014<\/strong><\/div>\n                <div class=\"mv-kv\"><span class=\"mv-kv-label\"><svg viewBox=\"0 0 24 24\" width=\"16\" height=\"16\" stroke=\"currentColor\" stroke-width=\"2\" fill=\"none\" stroke-linecap=\"round\" stroke-linejoin=\"round\" style=\"color:#64748b\"><path d=\"M16 13v8\"><\/path><path d=\"M8 13v8\"><\/path><path d=\"M12 15v8\"><\/path><path d=\"M20 16.58A5 5 0 0 0 18 7h-1.26A8 8 0 1 0 4 15.25\"><\/path><\/svg> Oborine danas<\/span><strong data-role=\"rain\">\u2014<\/strong><\/div>\n            <\/div>\n\n<div class=\"mv-measure-time\" data-role=\"weather-time\">\u2014<\/div>\n\n            <div class=\"mv-dhmz-ref\" data-role=\"dhmz-sisak-ref\" aria-live=\"polite\">\n                <div><strong>Meteorolo\u0161ka postaja DHMZ \u00b7 Sisak:<\/strong> <span class=\"mv-dhmz-ref-temp\" data-role=\"dhmz-sisak-temp\">\u2014<\/span> <span class=\"mv-dhmz-ref-at\" data-role=\"dhmz-sisak-at\"><\/span><\/div>\n                <div class=\"mv-dhmz-ref-grid\">\n                    <div class=\"mv-dhmz-ref-row\" data-role=\"dhmz-sisak-humidity-row\"><span>Vlaga<\/span><span data-role=\"dhmz-sisak-humidity\">\u2014<\/span><\/div>\n                    <div class=\"mv-dhmz-ref-row\" data-role=\"dhmz-sisak-wind-row\"><span>Vjetar<\/span><span data-role=\"dhmz-sisak-wind\">\u2014<\/span><\/div>\n                    <div class=\"mv-dhmz-ref-row\" data-role=\"dhmz-sisak-pressure-row\"><span>Tlak zraka<\/span><span data-role=\"dhmz-sisak-pressure\">\u2014<\/span><\/div>\n                    <div class=\"mv-dhmz-ref-row\" data-role=\"dhmz-sisak-rain-row\"><span>Oborina 24 h<\/span><span data-role=\"dhmz-sisak-rain\">\u2014<\/span><\/div>\n                <\/div>\n                <div class=\"mv-dhmz-ref-meta\" data-role=\"dhmz-sisak-time\">Slu\u017ebeno referentno mjerenje<\/div>\n                <div class=\"mv-dhmz-ref-stale\" data-role=\"dhmz-sisak-stale\">DHMZ jo\u0161 nije objavio novije mjerenje \u2014 ovo nije trenuta\u010dna temperatura.<\/div>\n                <div class=\"mv-dhmz-ref-note\" data-role=\"dhmz-sisak-rain-note\">Oborina: slu\u017ebeno 24-satno mjerenje DHMZ-a, nije isto \u0161to i Open-Meteo \u201eoborine danas\u201d.<\/div>\n            <\/div>\n\n<div class=\"mv-source-note\">Izvor: Open-Meteo \u00b7 Martinska Ves<\/div>\n\n<div class=\"mv-current-photo\">\n    <img decoding=\"async\"\n        src=\"https:\/\/martinskaves.hr\/wp-content\/uploads\/2023\/03\/Martinska-Ves-Most.jpg\"\n        alt=\"Most u Martinskoj Vesi\"\n        loading=\"lazy\"\n    >\n<\/div>\n\n<\/section>\n\n        <section class=\"mv-card mv-span-12 mv-card-nowcast\">\n            <div class=\"mv-nowcast-head\">\n                <h3 class=\"mv-card-title\" style=\"margin-bottom:0\">Sljede\u0107a 3 sata<\/h3>\n                <div class=\"mv-nowcast-sub\">15-minutna modelska prognoza za Martinsku Ves<\/div>\n            <\/div>\n            <div class=\"mv-nowcast-scroll\" aria-label=\"Prognoza za sljede\u0107a tri sata\">\n                <div class=\"mv-nowcast-track\" data-role=\"nowcast-track\">\n                    <div class=\"mv-nowcast-empty\">U\u010ditavanje kratkoro\u010dne prognoze\u2026<\/div>\n                <\/div>\n            <\/div>\n            <div class=\"mv-nowcast-legend\"><span><strong>Ki\u0161a<\/strong> = mm \/ 15 min<\/span><span><strong>Vjetar<\/strong> = brzina \/ udar km\/h<\/span><\/div>\n            <div class=\"mv-measure-time\" data-role=\"nowcast-time\">\u2014<\/div>\n            <div class=\"mv-source-note\">Izvor: Open-Meteo \u00b7 15-minutna modelska prognoza<\/div>\n        <\/section>\n\n        <section class=\"mv-card mv-span-5 mv-card-forecast\">\n            <h3 class=\"mv-card-title\">Prognoza 7 dana<\/h3>\n            <div class=\"mv-days\" data-role=\"days\"><\/div>\n            <div class=\"mv-measure-time\" data-role=\"forecast-time\">\u2014<\/div>\n            <div class=\"mv-source-note\">Izvor: Open-Meteo \/ modelska prognoza<\/div>\n        <\/section>\n\n        <section class=\"mv-card mv-span-12 mv-card-dubrovacak-detail\">\n            <header class=\"mv-dubx-head\">\n                <div class=\"mv-dubx-titles\">\n                    <div class=\"mv-dubx-eyebrow\">Mjerna postaja \u00b7 Sava<\/div>\n                    <h3 class=\"mv-dubx-title\">Dubrov\u010dak <span>detaljni vodostaj<\/span><\/h3>\n                <\/div>\n                <div class=\"mv-dubx-headside\">\n                    <div class=\"mv-dubx-status\" data-role=\"dub-detail-status\"><\/div>\n                    <div class=\"mv-dubx-clock\"><span>Lokalno vrijeme<\/span><strong data-role=\"dub-live-clock\">--:--:--<\/strong><\/div>\n                <\/div>\n            <\/header>\n\n            <div class=\"mv-dubx-hero\">\n                <div class=\"mv-dubx-main\">\n                    <div class=\"mv-dubx-label\">Trenutni vodostaj<\/div>\n                    <div class=\"mv-dubx-levelrow\">\n                        <strong class=\"mv-dubx-level\" data-role=\"dub-detail-level\">\u2014<\/strong>\n                        <span class=\"mv-dubx-arrow\" data-role=\"dub-detail-arrow\" aria-hidden=\"true\"><\/span>\n                    <\/div>\n                    <div class=\"mv-dubx-trend\"><strong data-role=\"dub-detail-trend\">\u2014<\/strong><span>od zadnjeg mjerenja<\/span><\/div>\n                    <div class=\"mv-dubx-gauge\" data-role=\"dub-detail-gauge\"><\/div>\n                    <div class=\"mv-dubx-meta\">\n                        <span>Slu\u017ebeno mjerenje<\/span>\n                        <strong data-role=\"dub-detail-time\">\u2014<\/strong>\n                    <\/div>\n                <\/div>\n\n                <div class=\"mv-dubx-metrics\" aria-label=\"Promjene vodostaja Dubrov\u010dak\">\n                    <div class=\"mv-dubx-metric\">\n                        <span data-role=\"dub-rate-hour-label\">Promjena u 24 h<\/span>\n                        <strong data-role=\"dub-rate-hour\">\u2014<\/strong>\n                    <\/div>\n                    <div class=\"mv-dubx-metric\">\n                        <span data-role=\"dub-rate-day-label\">Promjena u 3 dana<\/span>\n                        <strong data-role=\"dub-rate-day\">\u2014<\/strong>\n                    <\/div>\n                    <div class=\"mv-dubx-metric\">\n                        <span data-role=\"dub-rate-minute-label\">Promjena u 7 dana<\/span>\n                        <strong data-role=\"dub-rate-minute\">\u2014<\/strong>\n                    <\/div>\n                    <div class=\"mv-dubx-metric\">\n                        <span>Do pripremnog stanja<\/span>\n                        <strong data-role=\"dub-rate-preparation\">\u2014<\/strong>\n                    <\/div>\n                    <div class=\"mv-dubx-metric\">\n                        <span>Temperatura zraka<\/span>\n                        <strong data-role=\"dub-detail-air\">\u2014<\/strong>\n                    <\/div>\n                    <div class=\"mv-dubx-metric mv-dubx-metric-note\">\n                        <span>Napomena<\/span>\n                        <p>Promjene su izra\u010dunate iz slu\u017ebeno objavljenih mjerenja i nisu prognoza.<\/p>\n                    <\/div>\n                <\/div>\n            <\/div>\n\n            <div class=\"mv-dub-section\">\n                <div class=\"mv-dub-section-head\">\n                    <div class=\"mv-dub-section-title\">Shematski presjek rije\u010dnog korita<\/div>\n                    <div class=\"mv-dub-section-note\">Polo\u017eaj linija prati vodomjernu skalu u cm; presjek korita nije geodetski.<\/div>\n                <\/div>\n                <div class=\"mv-dub-cross-wrap\" data-role=\"dub-cross-section\">\n                    <div class=\"mv-dub-chart-empty\">U\u010ditavanje presjeka i slu\u017ebenih pragova\u2026<\/div>\n                <\/div>\n            <\/div>\n\n            <div class=\"mv-dub-detail-footer\">\n                Izvori: slu\u017ebeni vodostaj Hrvatske vode \u00b7 mVodostaji; usporedno mjerenje DHMZ Dubrov\u010dak Lijevi; temperatura zraka Open-Meteo \u00b7 Desni Dubrov\u010dak.<br>\n                Temperatura vode nije prikazana jer za postaju Dubrov\u010dak u trenutno kori\u0161tenom slu\u017ebenom javnom izvoru nije potvr\u0111en podatak temperature vode. Prikazat \u0107e se tek kada bude dostupan provjerljiv slu\u017ebeni izvor.\n            <\/div>\n        <\/section>\n\n        <section class=\"mv-card mv-span-12 mv-card-sava\">\n            <div class=\"mv-sava-head\">\n                <h3 class=\"mv-card-title\">Vodostaj Save \u2013 najnovija objavljena mjerenja<\/h3>\n                <div class=\"mv-sava-head-note\">Uzvodno \u2192 nizvodno \u00b7 dodirnite razdoblje u kartici za graf<\/div>\n            <\/div>\n\n            <div class=\"mv-river\" role=\"group\" aria-label=\"Pregled toka Save, od uzvodne prema nizvodnoj postaji\">\n                <div class=\"mv-river-dir\"><span>Uzvodno<\/span><span class=\"mv-river-dir-mid\">smjer toka Save<\/span><span>Nizvodno<\/span><\/div>\n                <div class=\"mv-river-nodes\" data-role=\"sava-strip-nodes\">\n                                        <button type=\"button\" class=\"mv-river-node\" data-sava-jump=\"slovenia\">\n                        <span class=\"mv-river-dot\"><\/span>\n                        <span class=\"mv-river-name\">\u010cate\u017e I<\/span>\n                        <span class=\"mv-river-level\">\u2014<\/span>\n                        <span class=\"mv-river-chg\"><\/span>\n                    <\/button>\n                                        <button type=\"button\" class=\"mv-river-node\" data-sava-jump=\"zagreb\">\n                        <span class=\"mv-river-dot\"><\/span>\n                        <span class=\"mv-river-name\">Zagreb<\/span>\n                        <span class=\"mv-river-level\">\u2014<\/span>\n                        <span class=\"mv-river-chg\"><\/span>\n                    <\/button>\n                                        <button type=\"button\" class=\"mv-river-node\" data-sava-jump=\"rugvica\">\n                        <span class=\"mv-river-dot\"><\/span>\n                        <span class=\"mv-river-name\">Rugvica<\/span>\n                        <span class=\"mv-river-level\">\u2014<\/span>\n                        <span class=\"mv-river-chg\"><\/span>\n                    <\/button>\n                                        <button type=\"button\" class=\"mv-river-node\" data-sava-jump=\"dubrovacak\">\n                        <span class=\"mv-river-dot\"><\/span>\n                        <span class=\"mv-river-name\">Dubrov\u010dak<\/span>\n                        <span class=\"mv-river-level\">\u2014<\/span>\n                        <span class=\"mv-river-chg\"><\/span>\n                    <\/button>\n                                        <button type=\"button\" class=\"mv-river-node\" data-sava-jump=\"crnac\">\n                        <span class=\"mv-river-dot\"><\/span>\n                        <span class=\"mv-river-name\">Crnac<\/span>\n                        <span class=\"mv-river-level\">\u2014<\/span>\n                        <span class=\"mv-river-chg\"><\/span>\n                    <\/button>\n                                    <\/div>\n            <\/div>\n\n            <div class=\"mv-water-wrap mv-water-sava\">\n                                <div class=\"mv-water-box\" data-role=\"water-slovenia\" tabindex=\"-1\">\n                    <div class=\"mv-water-top\">\n                        <div class=\"mv-water-name\">\u010cate\u017e I \u00b7 Slovenija<\/div>\n                                            <\/div>\n                                        <div class=\"mv-water-fresh\" data-role=\"water-slovenia-time\">\u2014<\/div>\n\n                    <div class=\"mv-water-levelrow\">\n                        <div class=\"mv-water-level\">\u2014<\/div>\n                        <span class=\"mv-water-arrow\" data-role=\"water-slovenia-arrow\" aria-hidden=\"true\"><\/span>\n                    <\/div>\n                    <div class=\"mv-water-rank\" data-role=\"water-slovenia-rank\"><\/div>                    <div class=\"mv-water-last\" data-role=\"water-slovenia-last\"><\/div>\n\n                    <div class=\"mv-water-changes\" data-role=\"water-slovenia-trend\"><\/div>\n                    <div data-role=\"water-slovenia-gauge\"><\/div>\n                    <div class=\"mv-water-status-wrap\" data-role=\"water-slovenia-status\"><\/div>\n                    <div class=\"mv-water-extra\" data-role=\"water-slovenia-extra\"><\/div>\n                                        <div class=\"mv-water-history\" data-role=\"water-slovenia-history\"><\/div>\n                <\/div>\n                    <div class=\"mv-water-box\" data-role=\"water-zagreb\" tabindex=\"-1\">\n                    <div class=\"mv-water-top\">\n                        <div class=\"mv-water-name\">Zagreb<\/div>\n                                            <\/div>\n                    <div class=\"mv-water-context\">uzvodna referentna postaja<\/div>                    <div class=\"mv-water-fresh\" data-role=\"water-zagreb-time\">\u2014<\/div>\n\n                    <div class=\"mv-water-levelrow\">\n                        <div class=\"mv-water-level\">\u2014<\/div>\n                        <span class=\"mv-water-arrow\" data-role=\"water-zagreb-arrow\" aria-hidden=\"true\"><\/span>\n                    <\/div>\n                    <div class=\"mv-water-rank\" data-role=\"water-zagreb-rank\"><\/div>                    <div class=\"mv-water-last\" data-role=\"water-zagreb-last\"><\/div>\n\n                    <div class=\"mv-water-changes\" data-role=\"water-zagreb-trend\"><\/div>\n                    <div data-role=\"water-zagreb-gauge\"><\/div>\n                    <div class=\"mv-water-status-wrap\" data-role=\"water-zagreb-status\"><\/div>\n                    <div class=\"mv-water-extra\" data-role=\"water-zagreb-extra\"><\/div>\n                                        <div class=\"mv-water-history\" data-role=\"water-zagreb-history\"><\/div>\n                <\/div>\n                    <div class=\"mv-water-box\" data-role=\"water-rugvica\" tabindex=\"-1\">\n                    <div class=\"mv-water-top\">\n                        <div class=\"mv-water-name\">Rugvica<\/div>\n                                            <\/div>\n                    <div class=\"mv-water-context\">BP10 \u00b7 D.10.10 \u00b7 desna obala Op\u0107ine<\/div>                    <div class=\"mv-water-fresh\" data-role=\"water-rugvica-time\">\u2014<\/div>\n\n                    <div class=\"mv-water-levelrow\">\n                        <div class=\"mv-water-level\">\u2014<\/div>\n                        <span class=\"mv-water-arrow\" data-role=\"water-rugvica-arrow\" aria-hidden=\"true\"><\/span>\n                    <\/div>\n                    <div class=\"mv-water-rank\" data-role=\"water-rugvica-rank\"><\/div>                    <div class=\"mv-water-last\" data-role=\"water-rugvica-last\"><\/div>\n\n                    <div class=\"mv-water-changes\" data-role=\"water-rugvica-trend\"><\/div>\n                    <div data-role=\"water-rugvica-gauge\"><\/div>\n                    <div class=\"mv-water-status-wrap\" data-role=\"water-rugvica-status\"><\/div>\n                    <div class=\"mv-water-extra\" data-role=\"water-rugvica-extra\"><\/div>\n                                        <div class=\"mv-water-history\" data-role=\"water-rugvica-history\"><\/div>\n                <\/div>\n                    <div class=\"mv-water-box\" data-role=\"water-dubrovacak\" tabindex=\"-1\">\n                    <div class=\"mv-water-top\">\n                        <div class=\"mv-water-name\">Dubrov\u010dak<\/div>\n                                            <\/div>\n                    <div class=\"mv-water-context\">BP10 \u00b7 D.10.4 \u00b7 lijeva obala Op\u0107ine<\/div>                    <div class=\"mv-water-fresh\" data-role=\"water-dubrovacak-time\">\u2014<\/div>\n\n                    <div class=\"mv-water-levelrow\">\n                        <div class=\"mv-water-level\">\u2014<\/div>\n                        <span class=\"mv-water-arrow\" data-role=\"water-dubrovacak-arrow\" aria-hidden=\"true\"><\/span>\n                    <\/div>\n                    <div class=\"mv-water-rank\" data-role=\"water-dubrovacak-rank\"><\/div>                    <div class=\"mv-water-last\" data-role=\"water-dubrovacak-last\"><\/div>\n\n                    <div class=\"mv-water-changes\" data-role=\"water-dubrovacak-trend\"><\/div>\n                    <div data-role=\"water-dubrovacak-gauge\"><\/div>\n                    <div class=\"mv-water-status-wrap\" data-role=\"water-dubrovacak-status\"><\/div>\n                    <div class=\"mv-water-extra\" data-role=\"water-dubrovacak-extra\"><\/div>\n                    <button type=\"button\" class=\"mv-water-link\" data-jump-detail>Detaljni prikaz i presjek korita \u2191<\/button>                    <div class=\"mv-water-history\" data-role=\"water-dubrovacak-history\"><\/div>\n                <\/div>\n                    <div class=\"mv-water-box\" data-role=\"water-crnac\" tabindex=\"-1\">\n                    <div class=\"mv-water-top\">\n                        <div class=\"mv-water-name\">Crnac<\/div>\n                                            <\/div>\n                                        <div class=\"mv-water-fresh\" data-role=\"water-crnac-time\">\u2014<\/div>\n\n                    <div class=\"mv-water-levelrow\">\n                        <div class=\"mv-water-level\">\u2014<\/div>\n                        <span class=\"mv-water-arrow\" data-role=\"water-crnac-arrow\" aria-hidden=\"true\"><\/span>\n                    <\/div>\n                    <div class=\"mv-water-rank\" data-role=\"water-crnac-rank\"><\/div>                    <div class=\"mv-water-last\" data-role=\"water-crnac-last\"><\/div>\n\n                    <div class=\"mv-water-changes\" data-role=\"water-crnac-trend\"><\/div>\n                    <div data-role=\"water-crnac-gauge\"><\/div>\n                    <div class=\"mv-water-status-wrap\" data-role=\"water-crnac-status\"><\/div>\n                    <div class=\"mv-water-extra\" data-role=\"water-crnac-extra\"><\/div>\n                                        <div class=\"mv-water-history\" data-role=\"water-crnac-history\"><\/div>\n                <\/div>\n                <\/div>\n\n                        <div class=\"mv-gauge-legend\" aria-label=\"Legenda traka pragova obrane od poplava\">\n                <span class=\"mv-gauge-legend-title\">Trake pragova:<\/span>\n                <span><span class=\"mv-swatch\" style=\"background:#d6e6f5\"><\/span>ispod pripremnog<\/span>\n                <span><span class=\"mv-swatch\" style=\"background:#f1dc8a\"><\/span>pripremno stanje<\/span>\n                <span><span class=\"mv-swatch\" style=\"background:#f4b46d\"><\/span>redovne mjere<\/span>\n                <span><span class=\"mv-swatch\" style=\"background:#ea8467\"><\/span>izvanredne mjere<\/span>\n                <span><span class=\"mv-swatch\" style=\"background:#c94848\"><\/span>izvanredno stanje<\/span>\n            <\/div>\n                            <details class=\"mv-water-help\">\n                <summary>Kako \u010ditati prikaz<\/summary>\n                <ul>\n                                        <li><strong>Redoslijed:<\/strong> postaje idu niz rijeku \u2013 od uzvodnog \u010cate\u017ea I (Slovenija) preko Zagreba, Rugvice i Dubrov\u010daka do Crnca. Vodni val putuje niz rijeku, pa se promjena na uzvodnoj postaji s vremenskim odmakom obi\u010dno vidi i nizvodno. To nije prognoza.<\/li>\n                                        <li><strong>Veliki broj<\/strong> je najnovije objavljeno slu\u017ebeno mjerenje (ne procjena). Uz njega pi\u0161e kada je izmjereno i koliko je staro.<\/li>\n                    <li><strong>Uz veliki broj<\/strong> strelica i vrijednost pokazuju promjenu od zadnjeg objavljenog mjerenja. <strong>U zadnja 24 h<\/strong> te <strong>3, 7 i 30 dana<\/strong> su razlike prema mjerenju otprilike toliko unatrag. Ra\u010duna se iz slu\u017ebenih mjerenja i nije prognoza.<\/li>\n                    <li><strong>Dodir na razdoblje<\/strong> (24 h, 3, 7 ili 30 dana) prebacuje graf te kartice na to razdoblje; odabrano razdoblje je podcrtano.<\/li>\n                    <li><strong>Traka pragova:<\/strong> kru\u017ei\u0107 pokazuje trenuta\u010dnu razinu, a boje su slu\u017ebeni pragovi obrane od poplava za mjerodavnu obrambenu dionicu. Pragovi nisu jedinstveno svojstvo fizi\u010dke postaje: ista postaja mo\u017ee imati druge pragove u drugom branjenom podru\u010dju ili dionici. Ispod trake pi\u0161e koliko je centimetara do sljede\u0107eg praga.<\/li>\n                                        <li><strong>Boja podloge kartice<\/strong> ozna\u010dava tri postaje s najve\u0107im porastom u zadnja 24 h. Najve\u0107i rast je naran\u010dast i s ja\u010dinom porasta prelazi prema crvenoj (oznaka \u201eJak porast\u201d); drugi je be\u017e, tre\u0107i siv. Slu\u017ebeno stanje obrane vidi se na traci pragova i u oznaci stanja.<\/li>\n                    <li><strong>Strelice:<\/strong> naran\u010dasta = rast, plava = pad, siva = stagnacija. Vodoravna strelica zna\u010di bez promjene, kosa manju promjenu (manje od 2 cm), a okomita ve\u0107u.<\/li>\n                                        <li><strong>Grafovi:<\/strong> \u201e24 sata\u201d, \u201e3 dana\u201d i \u201e7 dana\u201d prikazuju svako pojedina\u010dno slu\u017ebeno mjerenje u tom razdoblju. \u201e14 dana\u201d i \u201e30 dana\u201d prikazuju dnevni raspon: sjena je najni\u017ea i najvi\u0161a izmjerena razina toga dana, a linija je zadnje mjerenje toga dana. Nulta linija se ne forsira; isprekidana \u017euta linija je prag pripremnog stanja i vidi se kada je blizu opa\u017eenog raspona.<\/li>\n                    <li><strong>Traka toka<\/strong> na vrhu pokazuje razinu i promjenu u zadnja 24 h za svih pet postaja; dodir vodi na karticu postaje.<\/li>\n                <\/ul>\n                                <div class=\"mv-source-note\">Glavni izvor: Hrvatske vode \u00b7 mVodostaji; \u010cate\u017e I: ARSO (bez pragova u ovom prikazu). Dodatni DHMZ podatak prikazuje se gdje je automatska postaja dostupna.<\/div>\n                            <\/details>\n            <\/section>\n\n\n        <section class=\"mv-card mv-span-12 mv-card-odrakupa\">\n            <div class=\"mv-sava-head\">\n                <h3 class=\"mv-card-title\">Odra \u2013 Kupa<\/h3>\n                <div class=\"mv-sava-head-note\">Dodirnite razdoblje u kartici za graf<\/div>\n            <\/div>\n            <div class=\"mv-water-wrap mv-water-secondary\">\n                                <div class=\"mv-water-box\" data-role=\"water-odra\" tabindex=\"-1\">\n                    <div class=\"mv-water-top\">\n                        <div class=\"mv-water-name\">Odra \u00b7 Sifon Odra<\/div>\n                                            <\/div>\n                                        <div class=\"mv-water-fresh\" data-role=\"water-odra-time\">\u2014<\/div>\n\n                    <div class=\"mv-water-levelrow\">\n                        <div class=\"mv-water-level\">\u2014<\/div>\n                        <span class=\"mv-water-arrow\" data-role=\"water-odra-arrow\" aria-hidden=\"true\"><\/span>\n                    <\/div>\n                                        <div class=\"mv-water-last\" data-role=\"water-odra-last\"><\/div>\n\n                    <div class=\"mv-water-changes\" data-role=\"water-odra-trend\"><\/div>\n                    <div data-role=\"water-odra-gauge\"><\/div>\n                    <div class=\"mv-water-status-wrap\" data-role=\"water-odra-status\"><\/div>\n                    <div class=\"mv-water-extra\" data-role=\"water-odra-extra\"><\/div>\n                                        <div class=\"mv-water-history\" data-role=\"water-odra-history\"><\/div>\n                <\/div>\n                    <div class=\"mv-water-box\" data-role=\"water-kupa\" tabindex=\"-1\">\n                    <div class=\"mv-water-top\">\n                        <div class=\"mv-water-name\">Kupa \u00b7 Farka\u0161i\u0107<\/div>\n                                            <\/div>\n                                        <div class=\"mv-water-fresh\" data-role=\"water-kupa-time\">\u2014<\/div>\n\n                    <div class=\"mv-water-levelrow\">\n                        <div class=\"mv-water-level\">\u2014<\/div>\n                        <span class=\"mv-water-arrow\" data-role=\"water-kupa-arrow\" aria-hidden=\"true\"><\/span>\n                    <\/div>\n                                        <div class=\"mv-water-last\" data-role=\"water-kupa-last\"><\/div>\n\n                    <div class=\"mv-water-changes\" data-role=\"water-kupa-trend\"><\/div>\n                    <div data-role=\"water-kupa-gauge\"><\/div>\n                    <div class=\"mv-water-status-wrap\" data-role=\"water-kupa-status\"><\/div>\n                    <div class=\"mv-water-extra\" data-role=\"water-kupa-extra\"><\/div>\n                                        <div class=\"mv-water-history\" data-role=\"water-kupa-history\"><\/div>\n                <\/div>\n                <\/div>\n                        <div class=\"mv-gauge-legend\" aria-label=\"Legenda traka pragova obrane od poplava\">\n                <span class=\"mv-gauge-legend-title\">Trake pragova:<\/span>\n                <span><span class=\"mv-swatch\" style=\"background:#d6e6f5\"><\/span>ispod pripremnog<\/span>\n                <span><span class=\"mv-swatch\" style=\"background:#f1dc8a\"><\/span>pripremno stanje<\/span>\n                <span><span class=\"mv-swatch\" style=\"background:#f4b46d\"><\/span>redovne mjere<\/span>\n                <span><span class=\"mv-swatch\" style=\"background:#ea8467\"><\/span>izvanredne mjere<\/span>\n                <span><span class=\"mv-swatch\" style=\"background:#c94848\"><\/span>izvanredno stanje<\/span>\n            <\/div>\n                            <details class=\"mv-water-help\">\n                <summary>Kako \u010ditati prikaz<\/summary>\n                <ul>\n                                        <li><strong>Veliki broj<\/strong> je najnovije objavljeno slu\u017ebeno mjerenje (ne procjena). Uz njega pi\u0161e kada je izmjereno i koliko je staro.<\/li>\n                    <li><strong>Uz veliki broj<\/strong> strelica i vrijednost pokazuju promjenu od zadnjeg objavljenog mjerenja. <strong>U zadnja 24 h<\/strong> te <strong>3, 7 i 30 dana<\/strong> su razlike prema mjerenju otprilike toliko unatrag. Ra\u010duna se iz slu\u017ebenih mjerenja i nije prognoza.<\/li>\n                    <li><strong>Dodir na razdoblje<\/strong> (24 h, 3, 7 ili 30 dana) prebacuje graf te kartice na to razdoblje; odabrano razdoblje je podcrtano.<\/li>\n                    <li><strong>Traka pragova:<\/strong> kru\u017ei\u0107 pokazuje trenuta\u010dnu razinu, a boje su slu\u017ebeni pragovi obrane od poplava za mjerodavnu obrambenu dionicu. Pragovi nisu jedinstveno svojstvo fizi\u010dke postaje: ista postaja mo\u017ee imati druge pragove u drugom branjenom podru\u010dju ili dionici. Ispod trake pi\u0161e koliko je centimetara do sljede\u0107eg praga.<\/li>\n                                        <li><strong>Grafovi:<\/strong> \u201e24 sata\u201d, \u201e3 dana\u201d i \u201e7 dana\u201d prikazuju svako pojedina\u010dno slu\u017ebeno mjerenje u tom razdoblju. \u201e14 dana\u201d i \u201e30 dana\u201d prikazuju dnevni raspon: sjena je najni\u017ea i najvi\u0161a izmjerena razina toga dana, a linija je zadnje mjerenje toga dana. Nulta linija se ne forsira; isprekidana \u017euta linija je prag pripremnog stanja i vidi se kada je blizu opa\u017eenog raspona.<\/li>\n                    <li><strong>Traka toka<\/strong> na vrhu pokazuje razinu i promjenu u zadnja 24 h za svih pet postaja; dodir vodi na karticu postaje.<\/li>\n                <\/ul>\n                                <div class=\"mv-source-note\">Izvor: Hrvatske vode \u00b7 mVodostaji. Prikazuje se zadnje raspolo\u017eivo slu\u017ebeno mjerenje s vremenom.<\/div>\n                            <\/details>\n            <\/section>\n\n        <section class=\"mv-card mv-span-3 mv-card-air\">\n            <h3 class=\"mv-card-title\">Kvaliteta zraka<\/h3>\n\n            <div class=\"mv-air-place-control\">\n                <label>\n                    <span class=\"mv-air-place-label\">Odaberi naselje<\/span>\n                    <select class=\"mv-air-place-select\" data-air-place-select aria-label=\"Odaberi naselje za kvalitetu zraka\"><\/select>\n                <\/label>\n                <div class=\"mv-air-place-meta\" data-air-place-meta>Modelirana procjena za podru\u010dje Martinske Vesi \u00b7 CAMS Europe<\/div>\n            <\/div>\n\n            <div class=\"mv-aqi\">\n                <div class=\"mv-face\" data-role=\"face\"><svg viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><circle cx=\"12\" cy=\"12\" r=\"10\"><\/circle><line x1=\"8\" y1=\"15\" x2=\"16\" y2=\"15\"><\/line><line x1=\"9\" y1=\"9\" x2=\"9.01\" y2=\"9\"><\/line><line x1=\"15\" y1=\"9\" x2=\"15.01\" y2=\"9\"><\/line><\/svg><\/div>\n                <div>\n                    <div class=\"mv-aqi-number\" data-role=\"aqi\">\u2014<\/div>\n                    <div class=\"mv-muted\">Europski AQI<\/div>\n                    <div class=\"mv-aqi-label\"><span class=\"mv-pill\" data-role=\"aqi-pill\">DOBRA<\/span><\/div>\n                <\/div>\n            <\/div>\n\n            <div data-role=\"aqi-rows\"><\/div>\n\n            <details class=\"mv-water-help\"><summary>Kako \u010ditati prikaz i \u0161to su ove tvari<\/summary><div class=\"mv-aqi-help-h\">\u0160to pokazuje broj na vrhu<\/div><ul><li><strong>Europski AQI<\/strong> je zbirna ocjena zraka od 0 navi\u0161e \u2013 \u0161to manji broj, to \u010di\u0161\u0107i zrak. Odre\u0111uje ga ona tvar koja je trenuta\u010dno najlo\u0161ija, a ra\u010duna se po metodologiji Europske agencije za okoli\u0161 (EEA).<\/li><li><strong>Redovi ispod<\/strong> pokazuju svaku tvar zasebno: koliko je ima u zraku (mikrograma u kubnom metru, \u00b5g\/m\u00b3) i gdje je ta koli\u010dina na ljestvici od \u201eVrlo dobro\u201d do \u201eVrlo lo\u0161e\u201d. Kvadrati\u0107 na traci je trenuta\u010dna vrijednost.<\/li><\/ul><div class=\"mv-aqi-help-h\">\u0160to su te tvari i odakle dolaze<\/div><ul><li><strong>Lebde\u0107e \u010destice (PM10 i PM2.5)<\/strong> su sitni komadi\u0107i \u010da\u0111e, dima, pra\u0161ine i pepela koji lebde u zraku. PM10 su \u010destice manje od 10 mikrometara, a PM2.5 manje od 2,5 mikrometra; najsitnije dopiru duboko u plu\u0107a.<\/li><li><strong>Odakle \u010destice:<\/strong> \u010desti izvori su lo\u017eenje drva i ugljena, promet, industrija, spaljivanje biljnog i drugog otpada, pra\u0161ina s cesta i polja te povremeno prijenos pustinjskog pijeska. U hladnim i mirnim razdobljima one\u010di\u0161\u0107enje se lak\u0161e zadr\u017eava pri tlu.<\/li><li><strong>Du\u0161ikov dioksid (NO\u2082)<\/strong> nastaje pri izgaranju goriva, ponajvi\u0161e u prometu i lo\u017ei\u0161tima. Mo\u017ee nadra\u017eiti di\u0161ne putove, posebno kod osjetljivih osoba.<\/li><li><strong>Prizemni ozon (O\u2083)<\/strong> ne izlazi izravno iz dimnjaka ili ispuha, nego nastaje fotokemijskim reakcijama uz sun\u010devu svjetlost. Najvi\u0161e ga mo\u017ee biti tijekom toplih i sun\u010danih dana.<\/li><\/ul><div class=\"mv-aqi-help-h\">\u0160to razine zna\u010de<\/div><ul><li><strong>Vrlo dobro \/ Dobro:<\/strong> nema o\u010dekivanih zdravstvenih u\u010dinaka za ve\u0107inu ljudi.<\/li><li><strong>Umjereno:<\/strong> za ve\u0107inu bez ve\u0107ih u\u010dinaka; osjetljive osobe mogu primijetiti blage tegobe.<\/li><li><strong>Lo\u0161e:<\/strong> osjetljive osobe trebaju smanjiti napornu aktivnost na otvorenom.<\/li><li><strong>Vrlo lo\u0161e:<\/strong> mogu\u0107i su u\u010dinci i za manje osjetljive osobe; preporu\u010duje se ograni\u010diti napor na otvorenom.<\/li><\/ul><ul><li>Vrijednosti su modelska procjena za podru\u010dje Op\u0107ine Martinska Ves, a ne mjerenje zasebne lokalne postaje. Prikaz je op\u0107a informacija, ne osobni medicinski savjet.<\/li><\/ul><div class=\"mv-source-note\">Koncentracije: Open-Meteo \/ CAMS (Copernicus). Zbirni indeks: EEA. Pragovi razina po tvari: Njema\u010dki savezni ured za okoli\u0161 (Umweltbundesamt).<\/div><\/details>\n            <div class=\"mv-measure-time\" data-role=\"air-time\">\u2014<\/div>\n            <div class=\"mv-source-note\">Izvor: Open-Meteo \/ CAMS \u00b7 pragovi po one\u010di\u0161\u0107iva\u010du: UBA<\/div>\n        <\/section>\n\n        <section class=\"mv-card mv-span-12 mv-card-dubrovacak-charts\">\n            <div class=\"mv-dub-section\">\n                <div class=\"mv-dub-section-head\">\n                    <div class=\"mv-dub-section-title\">Detaljni grafikoni mjernog mjesta Dubrov\u010dak<\/div>\n                    <div class=\"mv-dub-section-note\">Graf se dopunjava \u010dim izvor objavi novo slu\u017ebeno mjerenje.<\/div>\n                <\/div>\n\n                <div class=\"mv-dub-charts\">\n                    <div class=\"mv-dub-24h-summary\" data-role=\"dub-24h-summary\"><\/div>\n\n                    <div class=\"mv-range-wrap\"><div class=\"mv-range-label\">Razdoblje prikaza<\/div><div class=\"mv-range\" role=\"group\" aria-label=\"Razdoblje prikaza\"><button type=\"button\" class=\"is-active\" data-dub-range-btn=\"24h\" aria-pressed=\"true\">24 sata<\/button><button type=\"button\" data-dub-range-btn=\"3d\" aria-pressed=\"false\">3 dana<\/button><button type=\"button\" data-dub-range-btn=\"7d\" aria-pressed=\"false\">7 dana<\/button><button type=\"button\" data-dub-range-btn=\"14d\" aria-pressed=\"false\">14 dana<\/button><button type=\"button\" data-dub-range-btn=\"30d\" aria-pressed=\"false\">30 dana<\/button><\/div><\/div>\n                    <div class=\"mv-dub-chart-card\" data-role=\"dub-chart-main\"><\/div>\n                    <div class=\"mv-dub-chart-card mv-dub-trend-status\" data-role=\"dub-trend-status\"><\/div>\n                <\/div>\n\n                <details class=\"mv-dub-help\"><summary>Kako \u010ditati prikaz<\/summary><ul><li><strong>Razdoblje prikaza<\/strong> (24 sata \/ 3 \/ 7 \/ 14 \/ 30 dana) mijenja sa\u017eetak na vrhu i glavni graf vodostaja.<\/li><li><strong>Linija<\/strong> za 24 sata, 3 i 7 dana prati pojedina\u010dna slu\u017ebena mjerenja (nije prognoza). Za 14 i 30 dana <strong>sjena<\/strong> je dnevni raspon (najni\u017ea i najvi\u0161a razina dana), a linija zadnje mjerenje dana.<\/li><li><strong>Graf automatski zumira stvarni raspon<\/strong> vodostaja. Slu\u017ebeni prag obrane prikazuje se na grafu samo kada je dovoljno blizu stvarnim mjerenjima, kako udaljeni prag ne bi spljo\u0161tio korisnu krivulju.<\/li><li><strong>Tendencija i sigurnosni status<\/strong> zamjenjuju veliki stup\u010dasti graf: prikazuju smjer u 24 sata, udaljenost do pripremnog stanja te najve\u0107i dnevni porast, pad i raspon u zadnjih 30 dana.<\/li><\/ul><div class=\"mv-source-note\">Izvor: Hrvatske vode \u00b7 mVodostaji (isto slu\u017ebeno mjerenje kao u pregledu iznad).<\/div><\/details>            <\/div>\n\n        <\/section>\n\n        <section class=\"mv-card mv-span-3 mv-card-pollen\">\n            <h3 class=\"mv-card-title\">Pelud \u2013 koncentracija<\/h3>\n\n            <div class=\"mv-air-place-control\">\n                <label>\n                    <span class=\"mv-air-place-label\">Odaberi naselje<\/span>\n                    <select class=\"mv-air-place-select\" data-air-place-select aria-label=\"Odaberi naselje za koncentraciju peludi\"><\/select>\n                <\/label>\n                <div class=\"mv-air-place-meta\" data-air-place-meta>Modelirana procjena za podru\u010dje Martinske Vesi \u00b7 CAMS Europe<\/div>\n            <\/div>\n\n            <div class=\"mv-pollen-summary\" data-role=\"pollen-summary\">\u2014<\/div>\n\n            <div data-role=\"pollen-rows\"><\/div>\n\n            <div class=\"mv-gauge-legend\" aria-label=\"Legenda razina peludi\"><span class=\"mv-gauge-legend-title\">Razine:<\/span><span><span class=\"mv-swatch\" style=\"background:#dcefe1\"><\/span>nisko<\/span><span><span class=\"mv-swatch\" style=\"background:#f6e6a8\"><\/span>umjereno<\/span><span><span class=\"mv-swatch\" style=\"background:#f3c08a\"><\/span>visoko<\/span><span><span class=\"mv-swatch\" style=\"background:#e08a8a\"><\/span>vrlo visoko<\/span><\/div>            <details class=\"mv-water-help\"><summary>Kako \u010ditati prikaz i \u0161to zna\u010di pelud<\/summary><ul><li><strong>Pragovi ovise o vrsti peludi<\/strong> \u2013 ambrozija i pelin mogu izazvati tegobe pri znatno ni\u017eim koncentracijama nego trave ili breza, zato ista brojka nema isto zna\u010denje za svaku biljku.<\/li><li><strong>Ambrozija:<\/strong> izrazito alergena korovna biljka; najve\u0107e optere\u0107enje obi\u010dno je u kasno ljeto i ranu jesen. <strong>Trave:<\/strong> jedan od naj\u010de\u0161\u0107ih uzroka sezonskih alergija, osobito u prolje\u0107e i rano ljeto.<\/li><li><strong>Pelin:<\/strong> korovna pelud koja se \u010de\u0161\u0107e pojavljuje ljeti i po\u010detkom jeseni. <strong>Breza:<\/strong> va\u017ena proljetna alergena pelud. <strong>Joha:<\/strong> rana sezonska pelud koja se mo\u017ee pojaviti ve\u0107 krajem zime i po\u010detkom prolje\u0107a.<\/li><li><strong>Nisko:<\/strong> simptome uglavnom osje\u0107aju vrlo osjetljive osobe. <strong>Umjereno<\/strong> i <strong>visoko:<\/strong> raste vjerojatnost i ja\u010dina simptoma. <strong>Vrlo visoko:<\/strong> izra\u017eena izlo\u017eenost za velik dio alergi\u010dnih osoba.<\/li><li>Prikazana koncentracija je trenuta\u010dno satno modelsko o\u010ditanje, a ne slu\u017ebeni dnevni prosjek na koji su pragovi izvorno kalibrirani \u2013 razina je procjena unutar tog okvira.<\/li><li>Open-Meteo\/CAMS trenuta\u010dno daje pouzdano usporediv modelski podatak za ovih pet skupina peludi; plugin zato ne prikazuje dodatne vrste kao da imaju stvarno mjerenje.<\/li><li>Prikaz je op\u0107a informacija o izlo\u017eenosti, ne osobni medicinski savjet.<\/li><\/ul><div class=\"mv-source-note\">Koncentracije: CAMS\/Copernicus (Open-Meteo). Pragovi razina: MeteoSwiss, prema klini\u010dkim smjernicama EAACI.<\/div><\/details>\n            <div class=\"mv-measure-time\" data-role=\"pollen-time\">\u2014<\/div>\n            <div class=\"mv-source-note\">Koncentracije: CAMS\/Copernicus (Open-Meteo) \u00b7 pragovi razina: MeteoSwiss<\/div>\n        <\/section>\n\n        <section class=\"mv-card mv-span-3 mv-card-soil\">\n            <h3 class=\"mv-card-title\">Stanje tla<\/h3>\n\n            <div class=\"mv-kv\"><span>\ud83c\udf21 Temp. tla \u00b7 6 cm<\/span><strong data-role=\"soil-temp-6\">\u2014<\/strong><\/div>\n            <div class=\"mv-kv\"><span>\ud83c\udf21 Temp. tla \u00b7 18 cm<\/span><strong data-role=\"soil-temp-18\">\u2014<\/strong><\/div>\n            <div class=\"mv-kv\"><span>\ud83c\udf21 Temp. tla \u00b7 54 cm<\/span><strong data-role=\"soil-temp-54\">\u2014<\/strong><\/div>\n            <div class=\"mv-kv\"><span>\ud83d\udca7 Vla\u017enost \u00b7 9\u201327 cm<\/span><strong data-role=\"soil-moisture-27\">\u2014<\/strong><\/div>\n            <div class=\"mv-kv\"><span>\ud83d\udca7 Vla\u017enost \u00b7 27\u201381 cm<\/span><strong data-role=\"soil-moisture-81\">\u2014<\/strong><\/div>\n            <div class=\"mv-kv\"><span>\ud83d\udca6 ET\u2080 danas<\/span><strong data-role=\"evapo\">\u2014<\/strong><\/div>\n            \n            <div class=\"mv-measure-time\" data-role=\"soil-time\">\u2014<\/div>\n            <div class=\"mv-source-note\">Izvor: Open-Meteo \u00b7 model tla<\/div>\n        <\/section>\n\n        <section class=\"mv-card mv-span-3 mv-card-uv\">\n            <h3 class=\"mv-card-title\">UV indeks<\/h3>\n\n            <div class=\"mv-uv-wrap\">\n                <div>\n                    <div class=\"mv-uv-number\" data-role=\"uv\">\u2014<\/div>\n                    <div class=\"mv-pill warn\" style=\"margin-top:8px\" data-role=\"uv-label\">UMJEREN<\/div>\n                <\/div>\n\n                <div class=\"mv-muted\" style=\"font-size:12px; line-height:1.4\">\n                    Za\u0161titite se: koristite kremu, \u0161e\u0161ir i izbjegavajte sunce 10\u201317 h.\n                <\/div>\n            <\/div>\n\n            <div class=\"mv-uv-scale\" data-role=\"uv-scale\"><\/div>\n            <div class=\"mv-uv-labels\" data-role=\"uv-labels\"><\/div>\n\n            <div class=\"mv-measure-time\" data-role=\"uv-time\">\u2014<\/div>\n            <div class=\"mv-source-note\">Izvor: Open-Meteo \u00b7 dnevni max<\/div>\n        <\/section>\n\n        <section class=\"mv-card mv-span-6 mv-card-rain\">\n            <div class=\"mv-rain-head\">\n                <h3 class=\"mv-card-title\">Oborine <span class=\"mv-rain-sub\" data-role=\"rain-sub\">\u2013 zadnjih 7 dana<\/span><\/h3>\n                <div class=\"mv-range mv-rain-range\" role=\"group\" aria-label=\"Razdoblje prikaza oborina\">\n                    <button type=\"button\" class=\"is-active\" data-rain-range=\"7d\" aria-pressed=\"true\">7 dana<\/button>\n                    <button type=\"button\" data-rain-range=\"30d\" aria-pressed=\"false\">30 dana<\/button>\n                    <button type=\"button\" data-rain-range=\"12m\" aria-pressed=\"false\">12 mjeseci<\/button>\n                <\/div>\n            <\/div>\n            <div class=\"mv-chart\" data-role=\"rain-chart\"><\/div>\n            <div class=\"mv-rain-svg\" data-role=\"rain-svg\" hidden><\/div>\n\n            <div data-role=\"rain-legend\"><div class=\"mv-gauge-legend\" aria-label=\"Legenda razreda oborina\"><span class=\"mv-gauge-legend-title\">Razredi:<\/span><span><span class=\"mv-swatch\" style=\"background:#e2e8f0\"><\/span>suho<\/span><span><span class=\"mv-swatch\" style=\"background:#a8d0f0\"><\/span>ki\u0161ni dan<\/span><span><span class=\"mv-swatch\" style=\"background:#4f93d1\"><\/span>obilna ki\u0161a<\/span><span><span class=\"mv-swatch\" style=\"background:#1f5c96\"><\/span>vrlo obilna ki\u0161a<\/span><\/div><\/div>\n\n            <div data-role=\"rain-stats\">\n                <div class=\"mv-kv\" style=\"border-bottom:0;padding-top:6px\"><span>Ukupno<\/span><strong data-role=\"rain-total\">\u2014<\/strong><\/div>\n                <div class=\"mv-kv\"><span>Ki\u0161nih dana (\u22651 mm)<\/span><strong data-role=\"rain-wetdays\">\u2014<\/strong><\/div>\n            <\/div>\n\n            <details class=\"mv-water-help\"><summary>Kako \u010ditati prikaz<\/summary><ul><li><strong>7 dana<\/strong> i <strong>30 dana<\/strong> prikazuju dnevnu koli\u010dinu oborina, uklju\u010duju\u0107i danas. To je prikaz pro\u0161lih i dana\u0161njih vrijednosti, ne prognoza unaprijed.<\/li><li><strong>12 mjeseci<\/strong> prikazuje ukupnu oborinu po mjesecima. Tamna crtica na svakom stupcu ozna\u010dava <strong>vi\u0161egodi\u0161nji prosjek<\/strong> za taj mjesec (DHMZ Sisak, 1949.\u20132024.). Teku\u0107i mjesec prikazan je svjetlije jer jo\u0161 traje.<\/li><li>Mjese\u010dne vrijednosti su modelska procjena za podru\u010dje Op\u0107ine Martinska Ves (Open-Meteo arhiv \/ ERA5), a ne mjerenje lokalnog ki\u0161omjera u Martinskoj Vesi.<\/li><li><strong>Razredi dnevne koli\u010dine oborina<\/strong> prate granice ETCCDI\/CLIMDEX (WMO): ki\u0161ni dan \u2265 1 mm, obilna ki\u0161a \u2265 10 mm, vrlo obilna ki\u0161a \u2265 20 mm.<\/li><li><strong>Ki\u0161nih dana<\/strong> broji dane s barem 1 mm oborine \u2013 standardnu klimatolo\u0161ku definiciju mokrog dana.<\/li><\/ul><div class=\"mv-source-note\">Izvor podataka: Open-Meteo (dnevno) i Open-Meteo arhiv \/ ERA5 (mjese\u010dno). Prosjek: DHMZ Sisak 1949.\u20132024. Razredi: ETCCDI\/CLIMDEX (WMO).<\/div><\/details>\n            <div class=\"mv-measure-time\" data-role=\"rain-history-time\">\u2014<\/div>\n            <div class=\"mv-source-note\">Izvor: Open-Meteo \u00b7 razredi oborina: WMO\/ETCCDI (CLIMDEX)<\/div>\n        <\/section>\n\n        <section class=\"mv-card mv-span-6 mv-card-wind\">\n            <h3 class=\"mv-card-title\">Vjetar<\/h3>\n            <div class=\"mv-wind-wrap\">\n                <div data-role=\"wind-rose\"><\/div>\n                <div>\n                    <div class=\"mv-kv\"><span>Smjer<\/span><strong data-role=\"wind-dir\">\u2014<\/strong><\/div>\n                    <div class=\"mv-kv\"><span>Brzina<\/span><strong data-role=\"wind-speed\">\u2014<\/strong><\/div>\n                    <div class=\"mv-kv\"><span>Udari<\/span><strong data-role=\"wind-gust\">\u2014<\/strong><\/div>\n                    <div class=\"mv-kv\"><span>Ja\u010dina<\/span><strong data-role=\"wind-desc\">\u2014<\/strong><\/div>\n                <\/div>\n            <\/div>\n\n            <div class=\"mv-beaufort-scale\" data-role=\"wind-beaufort\"><\/div>\n\n            <details class=\"mv-water-help\"><summary>Kako \u010ditati prikaz<\/summary><ul><li><strong>Beaufortova ljestvica<\/strong> je me\u0111unarodni standard (Svjetska meteorolo\u0161ka organizacija) za opisivanje ja\u010dine vjetra brojem od 0 (ti\u0161ina) do 12 (orkan), prema u\u010dincima na okolinu, ne samo brzinom.<\/li><li>Traka ispod pokazuje gdje se trenuta\u010dna brzina vjetra nalazi na toj ljestvici; broj i naziv (npr. \"4 Bf \u00b7 Umjeren vjetar\") zamjenjuju golu brzinu u km\/h opisom koji se odmah razumije.<\/li><li>Udari (poryv) mogu biti znatno ja\u010di od prosje\u010dne brzine \u2013 to je uobi\u010dajeno i ne zna\u010di gre\u0161ku u o\u010ditanju.<\/li><\/ul><div class=\"mv-source-note\">Brzina i smjer: Open-Meteo. Klasifikacija: Beaufortova ljestvica ja\u010dine vjetra (WMO, me\u0111unarodno standardizirana 1946.).<\/div><\/details>\n            <div class=\"mv-measure-time\" data-role=\"wind-time\">\u2014<\/div>\n            <div class=\"mv-source-note\">Izvor: Open-Meteo \u00b7 ja\u010dina prema Beaufortovoj ljestvici (WMO)<\/div>\n        <\/section>\n\n        <section class=\"mv-card mv-span-4 mv-card-warnings\">\n            <h3 class=\"mv-card-title\">Upozorenja DHMZ<\/h3>\n            <div class=\"mv-ok-box\" data-role=\"warnings-box\">\n                <div class=\"mv-warn-head\">\n                <div class=\"mv-warning-symbol is-unavailable\" data-role=\"warning-icon\" aria-hidden=\"true\"><svg viewBox=\"0 0 64 56\"><path d=\"M32 3 L61 53 H3 Z\" fill=\"currentColor\" stroke=\"rgba(15,23,42,.18)\" stroke-width=\"2\"><\/path><rect x=\"29.5\" y=\"17\" width=\"5\" height=\"20\" rx=\"2.5\" fill=\"var(--mv-warning-mark)\"><\/rect><circle cx=\"32\" cy=\"44\" r=\"3\" fill=\"var(--mv-warning-mark)\"><\/circle><\/svg><\/div>\n                <div class=\"mv-warn-headtext\">\n                    <div class=\"mv-warn-title\" data-role=\"warning-title\">PROVJERA...<\/div>\n                    <div class=\"mv-warn-text\" data-role=\"warning-text\">Dohva\u0107am slu\u017ebeni DHMZ CAP zapis.<\/div>\n                <\/div>\n                <\/div>\n                <div class=\"mv-warning-list\" data-role=\"warning-list\"><\/div>\n                <div class=\"mv-warning-advice\" data-role=\"warning-advice\" hidden>\n                    <div class=\"mv-warning-advice-title\">Preporuka DHMZ<\/div>\n                    <div class=\"mv-warning-advice-text\" data-role=\"warning-advice-text\"><\/div>\n                <\/div>\n                <div class=\"mv-warn-meta\">\n                    <span data-role=\"warning-time\">\u2014<\/span>\n                    <a href=\"https:\/\/meteo.hr\/naslovnica-upozorenja.php\" target=\"_blank\" rel=\"noopener noreferrer\">Vi\u0161e na meteo.hr \u2192<\/a>\n                <\/div>\n\n                <div class=\"mv-dhmz-radar\" data-role=\"dhmz-radar\">\n                    <div class=\"mv-dhmz-radar-head\">\n                        <div class=\"mv-dhmz-radar-title\">DHMZ radar \u00b7 kompozit<\/div>\n                        <div class=\"mv-dhmz-radar-meta\">slu\u017ebena radarska mjerenja \u00b7 5 min<\/div>\n                    <\/div>\n                    <div class=\"mv-dhmz-radar-frame\">\n                        <img data-role=\"dhmz-radar-img\"\n                             src=\"https:\/\/vrijeme.hr\/kompozit-stat.png\"\n                             alt=\"DHMZ radarska slika \u2013 kompozit\"\n                             loading=\"lazy\"\n                             decoding=\"async\">\n                        <div class=\"mv-dhmz-radar-badge\" data-role=\"dhmz-radar-badge\">DHMZ \u00b7 aktualno<\/div>\n                    <\/div>\n                    <div class=\"mv-dhmz-radar-controls\">\n                        <button type=\"button\" class=\"mv-dhmz-radar-play\" data-role=\"dhmz-radar-play\" disabled>\u25b6 Animacija<\/button>\n                        <a class=\"mv-dhmz-radar-link\"\n                           href=\"https:\/\/meteo.hr\/podaci.php?acto=anim&amp;el=kompozit&amp;param=radari&amp;section=podaci_mjerenja\"\n                           target=\"_blank\" rel=\"noopener noreferrer\">Otvori na DHMZ<\/a>\n                    <\/div>\n                    <div class=\"mv-dhmz-radar-note\" data-role=\"dhmz-radar-note\">U\u010ditavam slu\u017ebene DHMZ radarske frameove\u2026<\/div>\n                <\/div>\n            <\/div>\n        <\/section>\n\n        <section class=\"mv-card mv-span-12 mv-card-climate\">\n            <h3 class=\"mv-card-title\">Klimatolo\u0161ke srednje vrijednosti<\/h3>\n            <div class=\"mv-muted\" style=\"margin-top:-8px;margin-bottom:20px\" data-role=\"climate-subtitle\">\u2014<\/div>\n            <div class=\"mv-climate-grid\">\n                <div class=\"mv-climate-item\"><span>Srednja temp. (<span data-role=\"climate-month-a\">\u2014<\/span>)<\/span><strong data-role=\"climate-mean-temp\">\u2014<\/strong><\/div>\n                <div class=\"mv-climate-item\"><span>Apsolutni maksimum (<span data-role=\"climate-month-b\">\u2014<\/span>)<\/span><strong data-role=\"climate-max-temp\">\u2014<\/strong><\/div>\n                <div class=\"mv-climate-item\"><span>Apsolutni minimum (<span data-role=\"climate-month-c\">\u2014<\/span>)<\/span><strong data-role=\"climate-min-temp\">\u2014<\/strong><\/div>\n                <div class=\"mv-climate-item\"><span>Srednja oborina (<span data-role=\"climate-month-d\">\u2014<\/span>)<\/span><strong data-role=\"climate-mean-precip\">\u2014<\/strong><\/div>\n                <div class=\"mv-climate-item\"><span>Sun\u010dani sati (<span data-role=\"climate-month-e\">\u2014<\/span>)<\/span><strong data-role=\"climate-sun-hours\">\u2014<\/strong><\/div>\n                <div class=\"mv-climate-item\"><span>Razdoblje<\/span><strong data-role=\"climate-period\">\u2014<\/strong><\/div>\n            <\/div>\n            <div class=\"mv-source-note\">Izvor: DHMZ \u00b7 postaja Sisak. Povijesna referenca, nije mjerenje.<\/div>\n        <\/section>\n\n    <\/div>\n\n    <div class=\"mv-footer\">\n        <span>Podaci su informativnog karaktera. Za slu\u017ebene informacije obratite se nadle\u017enim institucijama.<\/span>\n        <span>Izvori: DHMZ, Hrvatske vode, Open-Meteo, CAMS.<\/span>\n    <\/div>\n\n    <script>\n    (function () {\n        const root = document.getElementById(\"mvmeteo-757f7c27-9c57-423d-a6cc-9b911b5cbd72\");\n        if (!root || root.dataset.initialized === '1') return;\n        root.dataset.initialized = '1';\n\n        const endpoint = root.dataset.endpoint;\n        const airEndpoint = root.dataset.airEndpoint;\n        const boundaryUrl = root.dataset.boundary;\n        let places = [];\n        let airLocations = [];\n        let selectedAirPlace = '';\n        let defaultAirPlace = 'martinska-ves';\n        let airRequestSerial = 0;\n\n        let map = null;\n        let boundaryLayer = null;\n        let outsideMaskLayer = null;\n        let placeLayer = null;\n        let infoMode = 'temperature';\n        let snapshotData = null;\n        \/* Odabrani raspon za \"Detaljni grafikoni mjernog mjesta Dubrov\u010dak\" (zaseban od\n           root.dataset.waterRange koji koristi glavna kartica Save). *\/\n        let dubRange = '24h';\n\n        let radarFrames = [];\n        let radarLayers = [];\n        let radarIndex = -1;\n        let radarTimer = null;\n        let radarReady = false;\n        let radarRefreshTimer = null;\n        let radarWasActive = false;\n        let muniBounds = null;\n        let mapUserMoved = false;\n\n        function qs(role) {\n            return root.querySelector('[data-role=\"' + role + '\"]');\n        }\n\n        function escapeHtml(value) {\n            return String(value ?? '')\n                .replace(\/&\/g, '&amp;')\n                .replace(\/<\/g, '&lt;')\n                .replace(\/>\/g, '&gt;')\n                .replace(\/\"\/g, '&quot;')\n                .replace(\/'\/g, '&#039;');\n        }\n\n        function fmt(value, decimals = 0) {\n            const n = Number(value);\n            if (!Number.isFinite(n)) return '\u2014';\n            return n.toLocaleString('hr-HR', {\n                minimumFractionDigits: decimals,\n                maximumFractionDigits: decimals\n            });\n        }\n\n        function airLocationBySlug(slug) {\n            return airLocations.find(item => item && item.slug === slug) || null;\n        }\n\n        function syncAirLocationControls() {\n            root.querySelectorAll('[data-air-place-select]').forEach(select => {\n                if (select.options.length !== airLocations.length) {\n                    select.innerHTML = airLocations.map(item =>\n                        '<option value=\"' + escapeHtml(item.slug) + '\">' + escapeHtml(item.name) + '<\/option>'\n                    ).join('');\n                }\n                if (selectedAirPlace && select.value !== selectedAirPlace) select.value = selectedAirPlace;\n            });\n            const loc = airLocationBySlug(selectedAirPlace);\n            root.querySelectorAll('[data-air-place-meta]').forEach(el => {\n                el.classList.remove('is-error');\n                el.innerHTML = loc\n                    ? 'Modelirana procjena za podru\u010dje <strong>' + escapeHtml(loc.name) + '<\/strong> \u00b7 CAMS Europe \u00b7 mre\u017ea pribli\u017eno 11 km'\n                    : 'Modelirana procjena \u00b7 CAMS Europe';\n            });\n        }\n\n        function setupAirLocations(items, preferredSlug) {\n            if (Array.isArray(items) && items.length) airLocations = items.filter(item => item && item.slug && item.name);\n            if (preferredSlug && airLocationBySlug(preferredSlug)) defaultAirPlace = preferredSlug;\n            if (!selectedAirPlace || !airLocationBySlug(selectedAirPlace)) selectedAirPlace = defaultAirPlace;\n            syncAirLocationControls();\n        }\n\n        function setAirLocationLoading(loading) {\n            root.querySelectorAll('[data-air-place-select]').forEach(select => { select.disabled = !!loading; });\n        }\n\n        function renderSelectedAir(payload) {\n            const aq = (payload && payload.air_quality && payload.air_quality.current) || {};\n            renderAQI(aq);\n            renderPollenCard(aq);\n            const stamp = aq.time ? 'Vrijeme podatka: ' + formatStamp(aq.time) : 'Dohva\u0107eno: ' + formatStamp(payload && payload.generated_at);\n            if (qs('air-time')) qs('air-time').textContent = stamp;\n            if (qs('pollen-time')) qs('pollen-time').textContent = stamp;\n            syncAirLocationControls();\n        }\n\n        function loadAirForPlace(slug) {\n            if (!airEndpoint || !airLocationBySlug(slug)) return;\n            selectedAirPlace = slug;\n            syncAirLocationControls();\n            setAirLocationLoading(true);\n            const serial = ++airRequestSerial;\n            const base = airEndpoint.replace(\/\\\/$\/, '') + '\/' + encodeURIComponent(slug);\n            const sep = base.includes('?') ? '&' : '?';\n            fetch(base + sep + '_mv=' + Date.now(), {\n                method:'GET', cache:'no-store', credentials:'same-origin',\n                headers:{'Accept':'application\/json','Cache-Control':'no-cache','Pragma':'no-cache'}\n            })\n            .then(r => r.ok ? r.json() : Promise.reject(new Error('HTTP ' + r.status)))\n            .then(payload => {\n                if (serial !== airRequestSerial) return;\n                renderSelectedAir(payload);\n            })\n            .catch(err => {\n                if (serial !== airRequestSerial) return;\n                console.error('MV Meteo \u2013 CAMS naselje', err);\n                root.querySelectorAll('[data-air-place-meta]').forEach(el => {\n                    el.classList.add('is-error');\n                    el.textContent = 'Podatak za odabrano naselje trenuta\u010dno nije dostupan.';\n                });\n            })\n            .finally(() => {\n                if (serial === airRequestSerial) setAirLocationLoading(false);\n            });\n        }\n\n        \/* Ikone vremena (\u010diste linijske ikone, Lucide stil). isDay: 1 dan, 0 no\u0107\n           (Open-Meteo \"is_day\"); bez podatka se pretpostavlja dan. *\/\n        function weatherIcon(code, isDay) {\n            code = Number(code);\n            const night = Number(isDay) === 0;\n            const svg = (inner) => '<svg viewBox=\"0 0 24 24\" width=\"1em\" height=\"1em\" fill=\"none\" stroke-width=\"1.9\" stroke-linecap=\"round\" stroke-linejoin=\"round\">' + inner + '<\/svg>';\n            const SUN = '#f59e0b', MOON = '#7c8db5', CLOUD = '#7b8ea3', RAIN = '#3b82f6', SNOW = '#60a5fa', STORM = '#8b5cf6';\n            const sun = svg('<g stroke=\"' + SUN + '\"><circle cx=\"12\" cy=\"12\" r=\"4.5\"\/><path d=\"M12 2v2M12 20v2M4.93 4.93l1.41 1.41M17.66 17.66l1.41 1.41M2 12h2M20 12h2M6.34 17.66l-1.41 1.41M19.07 4.93l-1.41 1.41\"\/><\/g>');\n            const moon = svg('<path stroke=\"' + MOON + '\" d=\"M20.5 14.1A8.5 8.5 0 1 1 9.9 3.5a6.6 6.6 0 0 0 10.6 10.6z\"\/>');\n            const cloudPath = '<path stroke=\"' + CLOUD + '\" d=\"M17.5 19H8a6 6 0 1 1 5.66-8h1.34a4 4 0 0 1 2.5 8z\"\/>';\n            const partlyDay = svg('<g stroke=\"' + SUN + '\"><path d=\"M8 2v1.5M2.8 4.8l1 1M1 10h1.5M13.2 4.8l-1 1\"\/><path d=\"M5.2 11.2A4 4 0 0 1 11 6.4\"\/><\/g><path stroke=\"' + CLOUD + '\" d=\"M18 20H9.5a4.5 4.5 0 1 1 3.9-6.8h.6a3.4 3.4 0 0 1 4 3.4 3.4 3.4 0 0 1 0 3.4z\"\/>');\n            const partlyNight = svg('<path stroke=\"' + MOON + '\" d=\"M11.6 8.6A5 5 0 0 1 5.4 3a5 5 0 1 0 6.9 6.3\"\/><path stroke=\"' + CLOUD + '\" d=\"M18 20H9.5a4.5 4.5 0 1 1 3.9-6.8h.6a3.4 3.4 0 0 1 4 3.4 3.4 3.4 0 0 1 0 3.4z\"\/>');\n            const cloud = svg(cloudPath);\n            const fog = svg('<path stroke=\"' + CLOUD + '\" d=\"M5 13.5A5.5 5.5 0 1 1 15.3 9h1.2a3.5 3.5 0 0 1 1.5 6.7\"\/><path stroke=\"' + CLOUD + '\" d=\"M4 18h12M7 21.5h12\"\/>');\n            const drizzle = svg('<path stroke=\"' + CLOUD + '\" d=\"M5 14.5A5.5 5.5 0 1 1 15.3 10h1.2a3.5 3.5 0 0 1 1.5 6.7\"\/><path stroke=\"' + RAIN + '\" d=\"M8 19v1M8 14v1M12 21v1M12 16v1M16 19v1M16 14v1\"\/>');\n            const rain = svg('<path stroke=\"' + CLOUD + '\" d=\"M5 14.5A5.5 5.5 0 1 1 15.3 10h1.2a3.5 3.5 0 0 1 1.5 6.7\"\/><path stroke=\"' + RAIN + '\" d=\"M8 15l-1.5 5M12 16l-1.5 5M16 15l-1.5 5\"\/>');\n            const snow = svg('<path stroke=\"' + CLOUD + '\" d=\"M5 14.5A5.5 5.5 0 1 1 15.3 10h1.2a3.5 3.5 0 0 1 1.5 6.7\"\/><path stroke=\"' + SNOW + '\" d=\"M8 16h.01M8 20h.01M12 18h.01M12 22h.01M16 16h.01M16 20h.01\" stroke-width=\"3\"\/>');\n            const storm = svg('<path stroke=\"' + CLOUD + '\" d=\"M5 14.5A5.5 5.5 0 1 1 15.3 10h1.2a3.5 3.5 0 0 1 1.5 6.7\"\/><path stroke=\"' + STORM + '\" d=\"M13 12l-3 5h4l-3 5\"\/>');\n\n            if (code === 0) return night ? moon : sun;\n            if (code === 1 || code === 2) return night ? partlyNight : partlyDay;\n            if (code === 3) return cloud;\n            if (code === 45 || code === 48) return fog;\n            if ([51,53,55,56,57].includes(code)) return drizzle;\n            if ([61,63,65,66,67,80,81,82].includes(code)) return rain;\n            if ([71,73,75,77,85,86].includes(code)) return snow;\n            if ([95,96,99].includes(code)) return storm;\n            return cloud;\n        }\n\n        function weatherDescription(code) {\n            code = Number(code);\n            if (code === 0) return 'Vedro';\n            if (code === 1) return 'Prete\u017eno vedro';\n            if (code === 2) return 'Djelomice obla\u010dno';\n            if (code === 3) return 'Obla\u010dno';\n            if (code === 45) return 'Magla';\n            if (code === 48) return 'Magla s injem';\n            if ([51,53,55].includes(code)) return 'Rosulja';\n            if ([56,57].includes(code)) return 'Ledena rosulja';\n            if ([61,63,65].includes(code)) return 'Ki\u0161a';\n            if ([66,67].includes(code)) return 'Ledena ki\u0161a';\n            if ([71,73,75,77].includes(code)) return 'Snijeg';\n            if ([80,81,82].includes(code)) return 'Pljuskovi';\n            if ([85,86].includes(code)) return 'Snje\u017eni pljuskovi';\n            if (code === 95) return 'Grmljavina';\n            if ([96,99].includes(code)) return 'Grmljavina s tu\u010dom';\n            return 'Promjenjivo';\n        }\n\n        function windDirection(deg) {\n            const dirs = ['N','NE','E','SE','S','SW','W','NW'];\n            const n = Number(deg);\n            if (!Number.isFinite(n)) return '\u2014';\n            return dirs[Math.round(n \/ 45) % 8];\n        }\n\n        \/* Beaufortova ljestvica ja\u010dine vjetra (WMO, me\u0111unarodni standard). max je gornja\n           granica raspona u km\/h; zadnja stavka (12) nema gornju granicu. *\/\n        const BEAUFORT_SCALE = [\n            {force:0,  max:1,        name:'Ti\u0161ina'},\n            {force:1,  max:5,        name:'Lahor'},\n            {force:2,  max:11,       name:'Povjetarac'},\n            {force:3,  max:19,       name:'Slab vjetar'},\n            {force:4,  max:28,       name:'Umjeren vjetar'},\n            {force:5,  max:38,       name:'Umjereno jak vjetar'},\n            {force:6,  max:49,       name:'Jak vjetar'},\n            {force:7,  max:61,       name:'\u017destok vjetar'},\n            {force:8,  max:74,       name:'Olujni vjetar'},\n            {force:9,  max:88,       name:'Jak olujni vjetar'},\n            {force:10, max:102,      name:'Oluja'},\n            {force:11, max:117,      name:'\u017destoka oluja'},\n            {force:12, max:Infinity, name:'Orkan'}\n        ];\n        \/* Boja po ja\u010dini: smireno plavo-zeleno \u2192 \u017euto \u2192 naran\u010dasto \u2192 crveno pri orkanskoj sili. *\/\n        const BEAUFORT_COLOR_STOPS = ['#8fb9d6','#7fc4a8','#f6e6a8','#f3ae72','#d9605f','#9f1c1c'];\n\n        function beaufortFor(speedKmh) {\n            const n = Number(speedKmh);\n            if (!Number.isFinite(n)) return null;\n            return BEAUFORT_SCALE.find(b => n <= b.max) || BEAUFORT_SCALE[BEAUFORT_SCALE.length - 1];\n        }\n\n        function beaufortColor(force) {\n            const idx = Math.min(BEAUFORT_COLOR_STOPS.length - 1, Math.round((force \/ 12) * (BEAUFORT_COLOR_STOPS.length - 1)));\n            return BEAUFORT_COLOR_STOPS[idx];\n        }\n\n        \/* Traka 0\u201312 Bf s markerom na trenuta\u010dnoj sili (isti generi\u010dki crta\u010d kao Kvaliteta zraka). *\/\n        function beaufortGaugeHtml(speedKmh) {\n            const b = beaufortFor(speedKmh);\n            const cutpoints = BEAUFORT_SCALE.slice(0, -1).map(x => x.max + 0.001);\n            const colors = BEAUFORT_SCALE.map(x => beaufortColor(x.force));\n            const gauge = segmentedGaugeHtml(speedKmh, cutpoints, colors);\n            const caption = b\n                ? '<div class=\"mv-beaufort-caption\"><span>Ja\u010dina vjetra<\/span><strong>' + escapeHtml(b.force + ' Bf \u00b7 ' + b.name) + '<\/strong><\/div>'\n                : '';\n            return gauge + caption;\n        }\n\n        function pollenLabel(value) {\n            const n = Number(value);\n            if (!Number.isFinite(n)) return '\u2014';\n            return fmt(n, n < 10 ? 1 : 0) + ' zrn\/m\u00b3';\n        }\n\n        \/* Pragovi razina optere\u0107enja peludi (zrn\/m\u00b3) \u2013 vidi PHP komentar uz\n           mvmeteo_pollen_legend_html() za izvor i napomenu o dnevnom prosjeku. *\/\n        const POLLEN_SPECIES = [\n            {role:'ragweed', label:'Ambrozija', hint:'Vrlo alergena korovna pelud; i ni\u017ee koncentracije mogu biti va\u017ene osjetljivim osobama.', color:'#e4392b', th:{moderate:6,  high:11, veryHigh:40}},\n            {role:'grass',   label:'Trave',     hint:'Jedna od naj\u010de\u0161\u0107ih skupina sezonske peludi, osobito u prolje\u0107e i rano ljeto.', color:'#f39c1d', th:{moderate:20, high:50, veryHigh:150}},\n            {role:'mugwort', label:'Pelin',     hint:'Korovna pelud koja je \u010de\u0161\u0107a tijekom ljeta i po\u010detkom jeseni.', color:'#f2c018', th:{moderate:6,  high:15, veryHigh:50}},\n            {role:'birch',   label:'Breza',     hint:'Va\u017ena proljetna alergena pelud drve\u0107a.', color:'#2ea34a', th:{moderate:11, high:70, veryHigh:300}},\n            {role:'alder',   label:'Joha',      hint:'Rana sezonska pelud drve\u0107a, \u010desto prisutna krajem zime i po\u010detkom prolje\u0107a.', color:'#1f7a8c', th:{moderate:11, high:70, veryHigh:250}}\n        ];\n        const POLLEN_RANK = {none:0, low:1, moderate:2, high:3, veryHigh:4};\n\n        function pollenLevel(value, th) {\n            const n = Number(value);\n            if (!Number.isFinite(n) || n < 1) return {tier:'none', label:'Izvan sezone', cls:'neutral'};\n            if (n < th.moderate) return {tier:'low', label:'Nisko', cls:'good'};\n            if (n < th.high) return {tier:'moderate', label:'Umjereno', cls:'warn'};\n            if (n < th.veryHigh) return {tier:'high', label:'Visoko', cls:'danger'};\n            return {tier:'veryHigh', label:'Vrlo visoko', cls:'severe'};\n        }\n\n        function pollenGaugeHtml(value, th) {\n            const n = Number(value);\n            const max = th.veryHigh * 1.15;\n            const pct = v => Math.max(0, Math.min(100, (v \/ max) * 100));\n            const stops = [\n                '#dcefe1 0%',\n                '#dcefe1 ' + pct(th.moderate).toFixed(2) + '%',\n                '#f6e6a8 ' + pct(th.moderate).toFixed(2) + '%',\n                '#f6e6a8 ' + pct(th.high).toFixed(2) + '%',\n                '#f3c08a ' + pct(th.high).toFixed(2) + '%',\n                '#f3c08a ' + pct(th.veryHigh).toFixed(2) + '%',\n                '#e08a8a ' + pct(th.veryHigh).toFixed(2) + '%',\n                '#e08a8a 100%'\n            ].join(',');\n            const markerLeft = pct(Number.isFinite(n) ? Math.max(n, 0) : 0);\n            return '<div class=\"mv-pollen-gauge\"><div class=\"mv-pollen-gauge-track\" style=\"background:linear-gradient(90deg,' + stops + ')\">' +\n                '<span class=\"mv-pollen-gauge-tick\" style=\"left:' + pct(th.moderate).toFixed(2) + '%\"><\/span>' +\n                '<span class=\"mv-pollen-gauge-tick\" style=\"left:' + pct(th.high).toFixed(2) + '%\"><\/span>' +\n                '<span class=\"mv-pollen-gauge-tick\" style=\"left:' + pct(th.veryHigh).toFixed(2) + '%\"><\/span>' +\n                '<span class=\"mv-pollen-gauge-marker\" style=\"left:' + markerLeft.toFixed(2) + '%\"><\/span>' +\n            '<\/div><\/div>';\n        }\n\n        function pollenRowHtml(sp, value) {\n            const lvl = pollenLevel(value, sp.th);\n            const n = Number(value);\n            const valueHtml = Number.isFinite(n)\n                ? escapeHtml(fmt(n, n < 10 ? 1 : 0)) + ' <small>zrn\/m\u00b3<\/small>'\n                : '\u2014';\n            return '<div class=\"mv-pollen-row\">' +\n                '<div class=\"mv-pollen-head\">' +\n                    '<span class=\"mv-pollen-name\"><span class=\"mv-dot\" style=\"background:' + sp.color + '\"><\/span>' + escapeHtml(sp.label) + '<\/span>' +\n                    '<span class=\"mv-pollen-value\">' + valueHtml + '<\/span>' +\n                '<\/div>' +\n                (sp.hint ? '<div class=\"mv-pollen-row-hint\">' + escapeHtml(sp.hint) + '<\/div>' : '') +\n                '<div class=\"mv-pollen-scale\">' + pollenGaugeHtml(value, sp.th) + '<span class=\"mv-pill ' + lvl.cls + '\">' + escapeHtml(lvl.label) + '<\/span><\/div>' +\n            '<\/div>';\n        }\n\n        \/* Redak po redak + naslovni sa\u017eetak (najozbiljnija vrsta trenuta\u010dno u sezoni). *\/\n        function renderPollenCard(aq) {\n            const rows = POLLEN_SPECIES.map(sp => {\n                const value = aq ? aq[sp.role + '_pollen'] : null;\n                return {sp: sp, value: value, lvl: pollenLevel(value, sp.th)};\n            });\n\n            const rowsEl = qs('pollen-rows');\n            if (rowsEl) rowsEl.innerHTML = rows.map(r => pollenRowHtml(r.sp, r.value)).join('');\n\n            const summaryEl = qs('pollen-summary');\n            if (summaryEl) {\n                const active = rows.filter(r => r.lvl.tier !== 'none')\n                    .sort((a, b) => POLLEN_RANK[b.lvl.tier] - POLLEN_RANK[a.lvl.tier] || Number(b.value) - Number(a.value));\n                if (!active.length) {\n                    summaryEl.innerHTML = '<span class=\"mv-pill neutral\">Izvan peludne sezone<\/span>';\n                } else {\n                    const top = active[0];\n                    summaryEl.innerHTML = 'Trenuta\u010dno najvi\u0161e: <strong>' + escapeHtml(top.sp.label) + '<\/strong> <span class=\"mv-pill ' + top.lvl.cls + '\">' + escapeHtml(top.lvl.label) + '<\/span>';\n                }\n            }\n        }\n\n        function aqiLabel(value) {\n            const n = Number(value);\n            const svgSmile = '<svg viewBox=\"0 0 24 24\" width=\"1em\" height=\"1em\" stroke=\"currentColor\" stroke-width=\"2\" fill=\"none\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><circle cx=\"12\" cy=\"12\" r=\"10\"><\/circle><path d=\"M8 14s1.5 2 4 2 4-2 4-2\"><\/path><line x1=\"9\" y1=\"9\" x2=\"9.01\" y2=\"9\"><\/line><line x1=\"15\" y1=\"9\" x2=\"15.01\" y2=\"9\"><\/line><\/svg>';\n            const svgNeutral = '<svg viewBox=\"0 0 24 24\" width=\"1em\" height=\"1em\" stroke=\"currentColor\" stroke-width=\"2\" fill=\"none\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><circle cx=\"12\" cy=\"12\" r=\"10\"><\/circle><line x1=\"8\" y1=\"15\" x2=\"16\" y2=\"15\"><\/line><line x1=\"9\" y1=\"9\" x2=\"9.01\" y2=\"9\"><\/line><line x1=\"15\" y1=\"9\" x2=\"15.01\" y2=\"9\"><\/line><\/svg>';\n            const svgSad = '<svg viewBox=\"0 0 24 24\" width=\"1em\" height=\"1em\" stroke=\"currentColor\" stroke-width=\"2\" fill=\"none\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><circle cx=\"12\" cy=\"12\" r=\"10\"><\/circle><path d=\"M16 16s-1.5-2-4-2-4 2-4 2\"><\/path><line x1=\"9\" y1=\"9\" x2=\"9.01\" y2=\"9\"><\/line><line x1=\"15\" y1=\"9\" x2=\"15.01\" y2=\"9\"><\/line><\/svg>';\n\n            if (!Number.isFinite(n)) return {label:'NEDOSTUPNO', cls:'warn', face:svgNeutral};\n            if (n <= 20) return {label:'DOBRA', cls:'', face:svgSmile};\n            if (n <= 40) return {label:'ZADOVOLJAVAJU\u0106A', cls:'', face:svgSmile};\n            if (n <= 60) return {label:'UMJERENA', cls:'warn', face:svgNeutral};\n            if (n <= 80) return {label:'LO\u0160A', cls:'danger', face:svgSad};\n            if (n <= 100) return {label:'VRLO LO\u0160A', cls:'danger', face:svgSad};\n            return {label:'IZNIMNO LO\u0160A', cls:'danger', face:svgSad};\n        }\n\n        \/* Generi\u010dka segmentirana traka (dijeli vizualni jezik s trakom pragova Save i peludi):\n           cutpoints su rastu\u0107e granice zona, colors ima jedan element vi\u0161e od cutpoints. *\/\n        function segmentedGaugeHtml(value, cutpoints, colors) {\n            const n = Number(value);\n            const top = cutpoints[cutpoints.length - 1];\n            const max = top * 1.15;\n            const pct = v => Math.max(0, Math.min(100, (v \/ max) * 100));\n            const stops = [];\n            let from = 0;\n            cutpoints.forEach((cp, i) => {\n                stops.push(colors[i] + ' ' + from.toFixed(2) + '%');\n                stops.push(colors[i] + ' ' + pct(cp).toFixed(2) + '%');\n                from = pct(cp);\n            });\n            stops.push(colors[colors.length - 1] + ' ' + from.toFixed(2) + '%');\n            stops.push(colors[colors.length - 1] + ' 100%');\n            const marker = pct(Number.isFinite(n) ? Math.max(n, 0) : 0);\n            const ticks = cutpoints.map(cp => '<span class=\"mv-scale-gauge-tick\" style=\"left:' + pct(cp).toFixed(2) + '%\"><\/span>').join('');\n            return '<div class=\"mv-scale-gauge\"><div class=\"mv-scale-gauge-track\" style=\"background:linear-gradient(90deg,' + stops.join(',') + ')\">' +\n                ticks + '<span class=\"mv-scale-gauge-marker\" style=\"left:' + marker.toFixed(2) + '%\"><\/span><\/div><\/div>';\n        }\n\n        \/* Pragovi po one\u010di\u0161\u0107iva\u010du (\u00b5g\/m\u00b3) \u2013 Njema\u010dki savezni ured za okoli\u0161 (UBA), ista\n           zdravstveno utemeljena metodologija kao europski AQI. Vrijednost svakog th je\n           PRVA vrijednost sljede\u0107e razine (isklju\u010divo ve\u0107e ili jednako), pa je \"good\" prag\n           gornja granica \"vrlo dobro\" + 1 itd. Vidi PHP komentar uz mvmeteo_aqi_help_html(). *\/\n        const AQI_POLLUTANTS = [\n            {role:'pm2_5',            key:'pm25', label:'PM2.5', name:'sitne lebde\u0107e \u010destice', hint:'Najfinije \u010destice dima i \u010da\u0111e; mogu prodrijeti duboko u plu\u0107a. \u010cesti izvori su ku\u0107na lo\u017ei\u0161ta, promet i spaljivanje.', th:{good:11,  moderate:21,  poor:26,  veryPoor:51}},\n            {role:'pm10',             key:'pm10', label:'PM10',  name:'lebde\u0107e \u010destice',       hint:'Pra\u0161ina, \u010da\u0111a i dim koji se zadr\u017eavaju u di\u0161nim putovima. Izvori uklju\u010duju lo\u017ei\u0161ta, promet, ceste i poljoprivrednu pra\u0161inu.', th:{good:21,  moderate:36,  poor:51,  veryPoor:101}},\n            {role:'nitrogen_dioxide', key:'no2',  label:'NO\u2082',   name:'du\u0161ikov dioksid',       hint:'Plin nastao izgaranjem goriva, posebno uz promet i lo\u017ei\u0161ta; mo\u017ee nadra\u017eiti di\u0161ne putove.', th:{good:21,  moderate:41,  poor:101, veryPoor:201}},\n            {role:'ozone',            key:'o3',   label:'O\u2083',    name:'prizemni ozon',         hint:'Nastaje fotokemijski uz sun\u010devu svjetlost; vi\u0161e vrijednosti \u010de\u0161\u0107e su za toplih, sun\u010danih dana.', th:{good:61,  moderate:121, poor:181, veryPoor:241}}\n        ];\n        const AQI_GAUGE_COLORS = ['#0f6b3a', '#8bc48a', '#f6e6a8', '#f3ae72', '#d9605f'];\n\n        function aqiPollutantLevel(value, th) {\n            const n = Number(value);\n            if (!Number.isFinite(n)) return {label:'\u2014', cls:'neutral'};\n            if (n < th.good) return {label:'Vrlo dobro', cls:'best'};\n            if (n < th.moderate) return {label:'Dobro', cls:'good'};\n            if (n < th.poor) return {label:'Umjereno', cls:'warn'};\n            if (n < th.veryPoor) return {label:'Lo\u0161e', cls:'danger'};\n            return {label:'Vrlo lo\u0161e', cls:'severe'};\n        }\n\n        function aqiRowHtml(p, value) {\n            const lvl = aqiPollutantLevel(value, p.th);\n            const n = Number(value);\n            const valueHtml = Number.isFinite(n) ? escapeHtml(fmt(n, 1)) + ' <small>\u00b5g\/m\u00b3<\/small>' : '\u2014';\n            const cutpoints = [p.th.good, p.th.moderate, p.th.poor, p.th.veryPoor];\n            return '<div class=\"mv-aqi-row\">' +\n                '<div class=\"mv-aqi-row-head\">' +\n                    '<span class=\"mv-aqi-row-name\">' + escapeHtml(p.label) + (p.name ? ' <em>' + escapeHtml(p.name) + '<\/em>' : '') + '<\/span>' +\n                    '<span class=\"mv-aqi-row-value\">' + valueHtml + '<\/span>' +\n                '<\/div>' +\n                (p.hint ? '<div class=\"mv-aqi-row-hint\">' + escapeHtml(p.hint) + '<\/div>' : '') +\n                '<div class=\"mv-aqi-row-scale\">' + segmentedGaugeHtml(value, cutpoints, AQI_GAUGE_COLORS) + '<span class=\"mv-pill ' + lvl.cls + '\">' + escapeHtml(lvl.label) + '<\/span><\/div>' +\n            '<\/div>';\n        }\n\n        function uvLabel(value) {\n            const n = Number(value);\n            if (!Number.isFinite(n)) return {label:'\u2014', cls:'warn'};\n            if (n <= 2) return {label:'NIZAK', cls:''};\n            if (n <= 5) return {label:'UMJEREN', cls:'warn'};\n            if (n <= 7) return {label:'VISOK', cls:'warn'};\n            if (n <= 10) return {label:'VRLO VISOK', cls:'danger'};\n            return {label:'EKSTREMAN', cls:'danger'};\n        }\n\n        function timeOnly(str) {\n            if (!str) return '\u2014';\n            const d = new Date(str);\n            if (isNaN(d.getTime())) return '\u2014';\n            return d.toLocaleTimeString('hr-HR', {hour:'2-digit', minute:'2-digit'});\n        }\n\n        function dateShort(str) {\n            if (!str) return '';\n            const d = new Date(str + 'T12:00:00');\n            if (isNaN(d.getTime())) return '';\n            return d.toLocaleDateString('hr-HR', {day:'2-digit', month:'2-digit'});\n        }\n\n        function dayName(str) {\n            if (!str) return '';\n            const d = new Date(str + 'T12:00:00');\n            if (isNaN(d.getTime())) return '';\n            return ['NED','PON','UTO','SRI','\u010cET','PET','SUB'][d.getDay()];\n        }\n\n        function makeWaterStatus(text, mode) {\n            const cls = mode === 'danger' ? 'mv-water-status is-danger'\n                     : mode === 'warn' ? 'mv-water-status is-warn'\n                     : 'mv-water-status';\n            const icon = mode === 'danger' ? '!' : mode === 'warn' ? '!' : '\u2713';\n            return '<span class=\"' + cls + '\"><span class=\"mv-water-status-icon\">' + icon + '<\/span><span class=\"mv-water-status-text\">' + text + '<\/span><\/span>';\n        }\n\n        \/* =========================================================\n           VODOSTAJI \u2013 pomo\u0107ne funkcije prikaza (v0.9.7)\n           ========================================================= *\/\n        \/* Redoslijed prati tok rijeke: uzvodno \u2192 nizvodno. *\/\n        const SAVA_ORDER = ['slovenia','zagreb','rugvica','dubrovacak','crnac'];\n        const SAVA_SHORT = {slovenia:'\u010cate\u017e I', zagreb:'Zagreb', rugvica:'Rugvica', dubrovacak:'Dubrov\u010dak', crnac:'Crnac'};\n        \/* Boje moraju odgovarati mvmeteo_water_threshold_colors() u PHP-u. *\/\n        const WATER_SAFE_COLOR = '#d6e6f5';\n        const WATER_THRESHOLDS = [\n            {key:'preparation',   name:'pripremnog stanja',  color:'#f1dc8a'},\n            {key:'regular',       name:'redovnih mjera',     color:'#f4b46d'},\n            {key:'extraordinary', name:'izvanrednih mjera',  color:'#ea8467'},\n            {key:'emergency',     name:'izvanrednog stanja', color:'#c94848'}\n        ];\n\n        \/* Number(null) je 0, a to bi la\u017eno pokazalo \u201e0 cm\u201d; zato null\/prazno tretiramo kao nepoznato. *\/\n        function toNum(value) {\n            if (value === null || value === undefined || value === '') return NaN;\n            return Number(value);\n        }\n\n        function signedCm(value) {\n            const n = toNum(value);\n            if (!Number.isFinite(n)) return '\u2014';\n            if (Math.abs(n) < 0.5) return '0 cm';\n            return (n > 0 ? '+' : '\u2212') + fmt(Math.abs(n), 0) + ' cm';\n        }\n\n        function waterDirection(value) {\n            const n = toNum(value);\n            if (!Number.isFinite(n)) return '';\n            if (n >= 0.5) return 'up';\n            if (n <= -0.5) return 'down';\n            return 'flat';\n        }\n\n        \/* Strelica prati smjer i ja\u010dinu promjene: vodoravna = stagnacija, kosa = manja promjena (< 2 cm), okomita = ve\u0107a. *\/\n        function waterArrowSvg(value) {\n            const n = toNum(value);\n            const head = '<svg viewBox=\"0 0 24 24\" width=\"17\" height=\"17\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2.2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" aria-hidden=\"true\">';\n            if (!Number.isFinite(n) || Math.abs(n) < 0.5) return head + '<line x1=\"5\" y1=\"12\" x2=\"19\" y2=\"12\"><\/line><polyline points=\"12 5 19 12 12 19\"><\/polyline><\/svg>';\n            if (n >= 2) return head + '<line x1=\"12\" y1=\"19\" x2=\"12\" y2=\"5\"><\/line><polyline points=\"5 12 12 5 19 12\"><\/polyline><\/svg>';\n            if (n > 0) return head + '<line x1=\"7\" y1=\"17\" x2=\"17\" y2=\"7\"><\/line><polyline points=\"7 7 17 7 17 17\"><\/polyline><\/svg>';\n            if (n <= -2) return head + '<line x1=\"12\" y1=\"5\" x2=\"12\" y2=\"19\"><\/line><polyline points=\"19 12 12 19 5 12\"><\/polyline><\/svg>';\n            return head + '<line x1=\"7\" y1=\"7\" x2=\"17\" y2=\"17\"><\/line><polyline points=\"17 7 17 17 7 17\"><\/polyline><\/svg>';\n        }\n\n        \/* Vrijeme mjerenja + koliko je staro (ra\u010duna se u pregledniku pri svakom osvje\u017eavanju). *\/\n        function waterFreshness(station) {\n            const measured = station && station.measured_at ? new Date(station.measured_at) : null;\n            if (!measured || Number.isNaN(measured.getTime())) {\n                return {cls:'', html: escapeHtml(station && station.display_time ? station.display_time : 'Vrijeme mjerenja nije potvr\u0111eno')};\n            }\n            const ageMin = Math.max(0, Math.round((Date.now() - measured.getTime()) \/ 60000));\n            let ageText;\n            if (ageMin < 1) ageText = 'upravo objavljeno';\n            else if (ageMin < 60) ageText = 'prije ' + ageMin + ' min';\n            else if (ageMin < 1440) {\n                const h = Math.floor(ageMin \/ 60), m = ageMin % 60;\n                ageText = 'prije ' + h + ' h' + (m ? ' ' + m + ' min' : '');\n            } else ageText = 'prije ' + Math.floor(ageMin \/ 1440) + ' d';\n\n            const clock = measured.toLocaleTimeString('hr-HR', {hour:'2-digit', minute:'2-digit'});\n            const sameDay = measured.toDateString() === new Date().toDateString();\n            const when = sameDay\n                ? 'danas ' + clock\n                : measured.toLocaleDateString('hr-HR', {day:'2-digit', month:'2-digit'}) + ' ' + clock;\n\n            let cls = 'is-fresh', suffix = '';\n            if (ageMin > 360) { cls = 'is-stale'; suffix = ' \u00b7 zadnji dostupan podatak'; }\n            else if (ageMin > 120) { cls = 'is-latest'; suffix = ' \u00b7 zadnje mjerenje'; }\n            return {cls: cls, html: escapeHtml(when + ' \u00b7 ' + ageText + suffix)};\n        }\n\n        \/* Tra\u017ei promjenu preko SVIH raspolo\u017eivih pojedina\u010dnih mjerenja (satni 24h zapis +\n           gusti do-8-dana zapis), spojenih i bez duplikata po to\u010dnom vremenu. Ni jedan izvor\n           sam za sebe ne mora pokrivati cijeli prozor: history_24h pokriva zadnjih ~24-30 h,\n           history_7d raste postupno kako radi cron, pa spajanje daje najbolju mogu\u0107u pokrivenost\n           umjesto da jedan rijedak izvor \"sakrije\" drugi, potpuniji. *\/\n        function waterHistoryPoints(station) {\n            const byTs = new Map();\n            const add = (rows) => {\n                (Array.isArray(rows) ? rows : []).forEach(row => {\n                    const ts = Number(row && row.timestamp || 0) * 1000;\n                    const level = toNum(row && row.level_cm);\n                    if (Number.isFinite(ts) && ts > 0 && Number.isFinite(level)) byTs.set(ts, level);\n                });\n            };\n            add(station && station.history_24h);\n            add(station && station.history_7d);\n            add(station && station.history_30d); \/* dnevni zapis kao krajnji fallback za du\u017ee prozore *\/\n            return Array.from(byTs, ([ts, level]) => ({ts, level})).sort((a, b) => a.ts - b.ts);\n        }\n\n        \/* Promjena prema najbli\u017eem slu\u017ebenom mjerenju otprilike prije `hours` sati. Nije prognoza. *\/\n        function waterChangeOver(station, hours, toleranceHours) {\n            const points = waterHistoryPoints(station);\n            const level = toNum(station && station.level_cm);\n            if (!points.length || !Number.isFinite(level)) return null;\n            const measured = station && station.measured_at ? new Date(station.measured_at).getTime() : NaN;\n            const latestTs = Number.isFinite(measured) ? measured : points[points.length - 1].ts;\n            const target = latestTs - hours * 3600000;\n            let best = null, bestDiff = Infinity;\n            points.forEach(p => {\n                if (p.ts >= latestTs - 600000) return; \/* osnovica mora biti jasno starija od zadnjeg mjerenja *\/\n                const diff = Math.abs(p.ts - target);\n                if (diff < bestDiff) { best = p; bestDiff = diff; }\n            });\n            if (!best || bestDiff > toleranceHours * 3600000) return null;\n            return level - best.level;\n        }\n\n        function waterChangeRow(label, value) {\n            const n = toNum(value);\n            const dir = waterDirection(n);\n            const cls = dir === 'up' ? 'is-up' : dir === 'down' ? 'is-down' : (Number.isFinite(n) ? 'is-flat' : 'is-none');\n            return '<div class=\"mv-water-change\"><span>' + escapeHtml(label) + '<\/span>' +\n                '<strong class=\"' + cls + '\">' + (Number.isFinite(n) ? waterArrowSvg(n) + '<b>' + escapeHtml(signedCm(n)) + '<\/b>' : '\u2014') + '<\/strong><\/div>';\n        }\n\n        \/* Traka pragova: kru\u017ei\u0107 = razina, boje = slu\u017ebeni pragovi, tekst = koliko je do sljede\u0107eg praga. *\/\n        function waterGaugeHtml(station) {\n            const limits = station && station.limits ? station.limits : {};\n            const level = toNum(station && station.level_cm);\n            const steps = WATER_THRESHOLDS\n                .map(s => Object.assign({}, s, {value: toNum(limits[s.key])}))\n                .filter(s => Number.isFinite(s.value))\n                .sort((a, b) => a.value - b.value);\n\n            if (!steps.length || !Number.isFinite(level)) {\n                return '<div class=\"mv-gauge-none\">Informativno mjerenje \u00b7 bez slu\u017ebenih pragova u ovom prikazu<\/div>';\n            }\n\n            const top = steps[steps.length - 1].value;\n            const max = top * 1.08;\n            const pct = v => Math.max(0, Math.min(100, (v \/ max) * 100));\n\n            const stops = [];\n            let from = 0;\n            let color = WATER_SAFE_COLOR;\n            steps.forEach(s => {\n                stops.push(color + ' ' + from.toFixed(2) + '% ' + pct(s.value).toFixed(2) + '%');\n                from = pct(s.value);\n                color = s.color;\n            });\n            stops.push(color + ' ' + from.toFixed(2) + '% 100%');\n\n            const next = steps.find(s => s.value > level);\n            const captionLabel = next ? 'Do ' + next.name : 'Iznad praga izvanrednog stanja';\n            const captionValue = next ? fmt(next.value - level, 0) + ' cm' : '+' + fmt(level - top, 0) + ' cm';\n\n            return '<div class=\"mv-gauge\" role=\"img\" aria-label=\"' + escapeHtml('Vodostaj ' + fmt(level, 0) + ' cm. ' + captionLabel + ': ' + captionValue + '.') + '\">' +\n                '<div class=\"mv-gauge-track\" style=\"background:linear-gradient(90deg,' + stops.join(',') + ')\">' +\n                    steps.map(s => '<span class=\"mv-gauge-tick\" style=\"left:' + pct(s.value).toFixed(2) + '%\"><\/span>').join('') +\n                    '<span class=\"mv-gauge-marker\" style=\"left:' + pct(level).toFixed(2) + '%\"><\/span>' +\n                '<\/div>' +\n                '<div class=\"mv-gauge-caption\"><span>' + escapeHtml(captionLabel) + '<\/span><strong>' + escapeHtml(captionValue) + '<\/strong><\/div>' +\n            '<\/div>';\n        }\n\n        function waterStatusClass(station) {\n            if (!station || !station.ok) return 'is-unavailable';\n            if (station.status === 'preparation') return 'is-preparation';\n            if (station.status === 'regular') return 'is-regular';\n            if (station.status === 'extraordinary') return 'is-extraordinary';\n            if (station.status === 'emergency') return 'is-emergency';\n            if (station.status === 'information') return 'is-info';\n            return '';\n        }\n\n        \/* Tolerancija raste s duljinom prozora jer du\u017ei prozori sve vi\u0161e ovise o dnevnom\n           (a ne satnom) zapisu, gdje se vrijeme mjerenja unutar dana mo\u017ee razlikovati. *\/\n        function waterRangeTolerance(range) {\n            if (range === '14d' || range === '30d') return 30;\n            if (range === '7d') return 9;\n            if (range === '3d') return 6;\n            return 3;\n        }\n\n        \/* Vrijednost promjene za odabrani raspon: 24h koristi isti temelj kao dosad\n           (najbli\u017ee mjerenje ~24 h unatrag), a dulji rasponi tra\u017ee mjerenje ~N dana unatrag\n           iz iste povijesti (gusta do 8 dana, dnevna dalje). Nije prognoza. *\/\n        function waterRangeChange(station, range) {\n            const cfg = WATER_RANGES[range] || WATER_RANGES['24h'];\n            return waterChangeOver(station, cfg.hours, waterRangeTolerance(range));\n        }\n\n        \/* Pregled toka Save: to\u010dka = stanje obrane, broj = razina, strelica = promjena za odabrani raspon. *\/\n        function renderSavaStrip(sava, range) {\n            const holder = qs('sava-strip-nodes');\n            if (!holder) return;\n            holder.innerHTML = SAVA_ORDER.map(key => {\n                const st = sava && sava[key] ? sava[key] : null;\n                const ok = !!(st && st.ok);\n                const chg = ok ? waterRangeChange(st, range) : NaN;\n                const dir = waterDirection(chg);\n                const chgHtml = Number.isFinite(chg)\n                    ? (dir === 'up' ? '\u2191 ' : dir === 'down' ? '\u2193 ' : '\u2192 ') + escapeHtml(fmt(Math.abs(chg), 0))\n                    : (ok ? '\u2014' : '');\n                const label = SAVA_SHORT[key] + (ok ? ': ' + fmt(st.level_cm, 0) + ' cm' : ': podatak nije dostupan');\n                return '<button type=\"button\" class=\"mv-river-node\" data-sava-jump=\"' + key + '\" aria-label=\"' + escapeHtml(label + '. Prika\u017ei karticu postaje.') + '\">' +\n                    '<span class=\"mv-river-dot ' + waterStatusClass(st) + '\"><\/span>' +\n                    '<span class=\"mv-river-name\">' + escapeHtml(SAVA_SHORT[key]) + '<\/span>' +\n                    '<span class=\"mv-river-level\">' + (ok ? escapeHtml(fmt(st.level_cm, 0)) + '<small>cm<\/small>' : '\u2014') + '<\/span>' +\n                    '<span class=\"mv-river-chg ' + (dir === 'up' ? 'is-up' : dir === 'down' ? 'is-down' : '') + '\">' + chgHtml + '<\/span>' +\n                '<\/button>';\n            }).join('');\n        }\n\n        function scrollToWaterTarget(el) {\n            if (!el) return;\n            const reduce = window.matchMedia && window.matchMedia('(prefers-reduced-motion: reduce)').matches;\n            el.scrollIntoView({behavior: reduce ? 'auto' : 'smooth', block: 'start'});\n            if (typeof el.focus === 'function') {\n                try { el.focus({preventScroll: true}); } catch (e) { \/* bez fokusa *\/ }\n            }\n        }\n\n        function radarTimeLabel(unixTime) {\n            const d = new Date(Number(unixTime) * 1000);\n            if (isNaN(d.getTime())) return '\u2014';\n            return d.toLocaleTimeString('hr-HR', {hour:'2-digit', minute:'2-digit'});\n        }\n\n        function updateRadarControls() {\n            const range = qs('radar-range');\n            const startEl = qs('radar-start');\n            const endEl = qs('radar-end');\n            const currentEl = qs('radar-current');\n\n            if (!range) return;\n\n            if (!radarFrames.length) {\n                range.min = 0; range.max = 0; range.value = 0; range.disabled = true;\n                if (startEl) startEl.textContent = '\u2014';\n                if (endEl) endEl.textContent = '\u2014';\n                if (currentEl) currentEl.textContent = '\u2014';\n                return;\n            }\n\n            range.min = 0;\n            range.max = Math.max(0, radarFrames.length - 1);\n            range.value = Math.max(0, radarIndex);\n            range.disabled = !radarReady;\n\n            if (startEl) startEl.textContent = radarTimeLabel(radarFrames[0].time);\n            if (endEl) endEl.textContent = radarTimeLabel(radarFrames[radarFrames.length - 1].time);\n            if (currentEl) {\n                const idx = Math.max(0, radarIndex);\n                currentEl.textContent = radarTimeLabel(radarFrames[idx].time);\n            }\n        }\n\n        \/* Svi kadrovi se dodaju odmah (prozirni), pa se plo\u010dice u\u010ditaju unaprijed;\n           animacija samo mijenja prozirnost \u2013 nema praznih bljeskova izme\u0111u kadrova. *\/\n        function showRadarFrame(index) {\n            if (!map || !radarReady || !radarLayers.length) return;\n            index = Math.max(0, Math.min(index, radarLayers.length - 1));\n            radarLayers.forEach(layer => { if (!map.hasLayer(layer)) layer.addTo(map); });\n            radarLayers.forEach((layer, i) => layer.setOpacity(i === index ? 0.7 : 0));\n            radarIndex = index;\n            if (outsideMaskLayer?.bringToFront) outsideMaskLayer.bringToFront();\n            if (boundaryLayer?.bringToFront) boundaryLayer.bringToFront();\n            if (placeLayer?.bringToFront) placeLayer.bringToFront();\n            updateRadarControls();\n        }\n\n        function stopRadarAnimation() {\n            if (radarTimer) {\n                clearInterval(radarTimer);\n                radarTimer = null;\n            }\n            const btn = root.querySelector('[data-action=\"radar-play\"]');\n            if (btn) {\n                btn.innerHTML = '<svg viewBox=\"0 0 24 24\" width=\"16\" height=\"16\" fill=\"currentColor\"><path d=\"M8 5v14l11-7z\"><\/path><\/svg>';\n                btn.setAttribute('aria-label', 'Pokreni radarsku animaciju');\n            }\n        }\n\n        function toggleRadarAnimation() {\n            if (!radarReady || !radarFrames.length) return;\n            const btn = root.querySelector('[data-action=\"radar-play\"]');\n            if (radarTimer) { stopRadarAnimation(); return; }\n            if (btn) {\n                btn.innerHTML = '<svg viewBox=\"0 0 24 24\" width=\"16\" height=\"16\" fill=\"currentColor\"><path d=\"M6 19h4V5H6v14zm8-14v14h4V5h-4z\"><\/path><\/svg>';\n                btn.setAttribute('aria-label', 'Zaustavi radarsku animaciju');\n            }\n            radarTimer = setInterval(function () {\n                const next = radarIndex >= radarLayers.length - 1 ? 0 : radarIndex + 1;\n                showRadarFrame(next);\n            }, 850);\n        }\n\n        function loadRadarFrames() { \/* RainViewer uklonjen \u2013 vidi initMap(). *\/ }\n\n        function hideRadarLayer() {\n            stopRadarAnimation();\n            radarLayers.forEach(layer => { if (map && map.hasLayer(layer)) map.removeLayer(layer); });\n        }\n\n        function setMapMode(mode) {\n            infoMode = mode;\n            root.querySelectorAll('[data-mapmode]').forEach(btn => {\n                btn.classList.toggle('is-active', btn.getAttribute('data-mapmode') === mode);\n            });\n            const controls = qs('radar-controls');\n            if (mode === 'radar') {\n                if (controls) controls.classList.add('is-visible');\n                \/* Radar je grube rezolucije (izvor daje najvi\u0161e zoom 7), pa se prikazuje\n                   regionalno: vidi se oborina koja dolazi prema op\u0107ini, a ne mutni blokovi. *\/\n                if (map) map.setView(muniBounds ? muniBounds.getCenter() : map.getCenter(), map.getSize().x < 520 ? 8.5 : 9.25, {animate:true});\n                if (radarReady && radarFrames.length) {\n                    radarIndex = radarFrames.length - 1;\n                    showRadarFrame(radarIndex);\n                }\n                if (!radarRefreshTimer) radarRefreshTimer = setInterval(loadRadarFrames, 10 * 60 * 1000);\n            } else {\n                if (controls) controls.classList.remove('is-visible');\n                hideRadarLayer();\n                if (radarRefreshTimer) { clearInterval(radarRefreshTimer); radarRefreshTimer = null; }\n                if (map && muniBounds && !mapUserMoved) fitMunicipality(true);\n                else if (map && muniBounds && radarWasActive) fitMunicipality(true);\n            }\n            radarWasActive = (mode === 'radar');\n            renderPlaceLabels();\n        }\n\n        function renderPlaceLabels() {\n            if (!window.L || !map) return;\n            if (placeLayer) placeLayer.clearLayers();\n            else placeLayer = L.layerGroup([], {pane:'mvLabelsPane'}).addTo(map);\n\n            const fallback = snapshotData?.forecast?.current || {};\n\n            places.forEach(place => {\n                const current = place.current || fallback;\n                let metric = '';\n\n                if (infoMode === 'temperature') {\n                    metric = '<span class=\"mv-weather-symbol\" aria-hidden=\"true\">' + weatherIcon(current.weather_code, current.is_day ?? fallback.is_day) + '<\/span>' +\n                             '<span>' + fmt(current.temperature_2m, 0) + '\u00b0C<\/span>';\n                } else if (infoMode === 'wind') {\n                    const deg = Number(current.wind_direction_10m) || 0;\n                    metric = '<span class=\"mv-wind-arrow\" style=\"transform:rotate(' + deg + 'deg)\" aria-hidden=\"true\"><svg viewBox=\"0 0 24 24\"><path d=\"M12 2L19 21L12 17L5 21L12 2Z\"><\/path><\/svg><\/span>' +\n                             '<span>' + fmt(current.wind_speed_10m, 0) + ' km\/h<\/span>';\n                } else if (infoMode === 'rain') {\n                    const p = Number(current.precipitation) || 0;\n                    const symbol = p > 0.05 ? '<svg viewBox=\"0 0 24 24\" width=\"1em\" height=\"1em\" stroke=\"currentColor\" stroke-width=\"2\" fill=\"none\"><path d=\"M12 15v8\"><\/path><\/svg>' : '';\n                    metric = '<span class=\"mv-weather-symbol\" aria-hidden=\"true\">' + symbol + '<\/span>' +\n                             '<span>' + fmt(p, 1) + ' mm<\/span>';\n                }\n\n                const dx = Number(place.dx) || 0;\n                const dy = Number(place.dy) || 0;\n                const metricHtml = metric ? '<div class=\"mv-place-weather\">' + metric + '<\/div>' : '';\n                const html = '<div class=\"mv-place-label-inner\" style=\"--mv-dx:' + dx + 'px;--mv-dy:' + dy + 'px\">' +\n                             '<div>' + place.name + '<\/div>' + metricHtml + '<\/div>';\n\n                const icon = L.divIcon({ className:'mv-place-label', html:html, iconSize:[1,1], iconAnchor:[0,0] });\n                L.marker([place.lat, place.lng], { pane:'mvLabelsPane', icon:icon, interactive:false }).addTo(placeLayer);\n            });\n            if (placeLayer.bringToFront) placeLayer.bringToFront();\n        }\n\n        \/* Op\u0107ina \u0161to ve\u0107a u okviru: gore vi\u0161e mjesta za natpise naselja, sa strane malo. *\/\n        function fitMunicipality(animate) {\n            if (!map || !muniBounds) return;\n            const narrow = map.getSize().x < 520;\n            map.fitBounds(muniBounds, {\n                paddingTopLeft: [narrow ? 12 : 28, narrow ? 44 : 56],\n                paddingBottomRight: [narrow ? 12 : 28, narrow ? 28 : 36],\n                animate: !!animate\n            });\n        }\n\n        function initMap() {\n            if (!window.L) return;\n            \/* zoomSnap 0.25: op\u0107ina ispunjava okvir (s cijelim brojevima zooma ostajalo je\n               puno praznog prostora oko granice). *\/\n            map = L.map(qs('map'), { zoomControl:true, attributionControl:true, zoomSnap:0.25, zoomDelta:0.5 }).setView([45.58410, 16.37030], 12);\n            map.on('dragstart', () => { mapUserMoved = true; });\n            map.getContainer().addEventListener('wheel', () => { mapUserMoved = true; }, {passive:true});\n            map.on('zoomstart', e => { if (e && e.originalEvent) mapUserMoved = true; });\n            let fitTimer = null;\n            window.addEventListener('resize', () => {\n                clearTimeout(fitTimer);\n                fitTimer = setTimeout(() => { map.invalidateSize(); if (!mapUserMoved && infoMode !== 'radar') fitMunicipality(false); }, 200);\n            });\n\n            map.createPane('mvRadarPane'); map.getPane('mvRadarPane').style.zIndex = 430; map.getPane('mvRadarPane').style.pointerEvents = 'none';\n            map.createPane('mvMaskPane'); map.getPane('mvMaskPane').style.zIndex = 450; map.getPane('mvMaskPane').style.pointerEvents = 'none';\n            map.createPane('mvBoundaryPane'); map.getPane('mvBoundaryPane').style.zIndex = 470; map.getPane('mvBoundaryPane').style.pointerEvents = 'none';\n            map.createPane('mvLabelsPane'); map.getPane('mvLabelsPane').style.zIndex = 510; map.getPane('mvLabelsPane').style.pointerEvents = 'none';\n            map.createPane('mvFallbackPane'); map.getPane('mvFallbackPane').style.zIndex = 180;\n            map.createPane('mvBasePane'); map.getPane('mvBasePane').style.zIndex = 200;\n\n            const osmFallback = L.tileLayer('https:\/\/tile.openstreetmap.org\/{z}\/{x}\/{y}.png', { maxZoom:19, pane:'mvFallbackPane', opacity:1, attribution:'&copy; OpenStreetMap contributors' }).addTo(map);\n            const esri = L.tileLayer('https:\/\/{s}.basemaps.cartocdn.com\/rastertiles\/voyager\/{z}\/{x}\/{y}.png?key=cb1_2bys_1_24f193e3e5a9fea7de509b93', { maxZoom:20, subdomains:'abcd', pane:'mvBasePane', opacity:1, attribution:'&copy; CARTO' });\n            \n            let cartoTileErrors = 0;\n            esri.on('tileerror', function () { cartoTileErrors++; if (cartoTileErrors >= 3 && map.hasLayer(esri)) map.removeLayer(esri); });\n            esri.on('tileload', function () { cartoTileErrors = 0; });\n            esri.addTo(map);\n\n            if (boundaryUrl) {\n                fetch(boundaryUrl, {cache:'no-store'})\n                    .then(r => r.ok ? r.json() : null)\n                    .then(geojson => {\n                        if (!geojson) { renderPlaceLabels(); return; }\n                        const geometry = geojson?.features?.[0]?.geometry;\n                        if (geometry?.type === 'Polygon' && Array.isArray(geometry.coordinates?.[0])) {\n                            const hole = geometry.coordinates[0].map(c => [c[1], c[0]]);\n                            const world = [[90,-180],[90,180],[-90,180],[-90,-180]];\n                            outsideMaskLayer = L.polygon([world, hole], { pane:'mvMaskPane', stroke:false, fillColor:'#d9e7f2', fillOpacity:.25, fillRule:'evenodd', interactive:false }).addTo(map);\n                        }\n                        boundaryLayer = L.geoJSON(geojson, { pane:'mvBoundaryPane', style:{ color:'#2e74bd', weight:3.2, opacity:1, fill:false, lineCap:'square', lineJoin:'miter' } }).addTo(map);\n                        const bounds = boundaryLayer.getBounds();\n                        if (bounds.isValid()) { muniBounds = bounds; fitMunicipality(false); }\n                        if (outsideMaskLayer?.bringToFront) outsideMaskLayer.bringToFront();\n                        if (boundaryLayer?.bringToFront) boundaryLayer.bringToFront();\n                        renderPlaceLabels();\n                    }).catch(() => renderPlaceLabels());\n            } else {\n                renderPlaceLabels();\n            }\n\n            const attr = map.attributionControl.getContainer();\n            if (attr) attr.classList.add('mv-leaflet-attribution');\n            \/* RainViewer uklonjen (v0.17.1): besplatni API od 2026. je samo za osobnu i\n               obrazovnu upotrebu. Radar se prikazuje iz slu\u017ebenog DHMZ kompozita. *\/\n        }\n\n        function formatStamp(value) {\n            if (!value) return '\u2014';\n            const d = new Date(value);\n            if (Number.isNaN(d.getTime())) return String(value);\n            return d.toLocaleString('hr-HR', {day:'2-digit',month:'2-digit',year:'numeric',hour:'2-digit',minute:'2-digit'});\n        }\n\n        function waterHistoryDateLabel(value) {\n            if (!value) return '';\n            const parts = String(value).split('-');\n            return parts.length === 3 ? parts[2] + '.' + parts[1] + '.' : String(value);\n        }\n\n        function waterHourlyTimeLabel(row) {\n            if (!row) return '';\n            if (row.time) return String(row.time);\n            if (row.measured_at) {\n                const d = new Date(row.measured_at);\n                if (!Number.isNaN(d.getTime())) return d.toLocaleTimeString('hr-HR', {hour:'2-digit', minute:'2-digit'});\n            }\n            return '';\n        }\n\n        function waterHourlyDateTimeLabel(row) {\n            if (!row) return '';\n            const ts = Number(row.timestamp) * 1000;\n            const d = Number.isFinite(ts) && ts > 0 ? new Date(ts) : (row.measured_at ? new Date(row.measured_at) : null);\n            if (!d || Number.isNaN(d.getTime())) return waterHourlyTimeLabel(row);\n            return d.toLocaleDateString('hr-HR', {day:'2-digit', month:'2-digit'}) + ' ' + d.toLocaleTimeString('hr-HR', {hour:'2-digit', minute:'2-digit'});\n        }\n\n        \/* Jedan crta\u010d za sve raspone: 'hourly' i 'dense' crtaju niz pojedina\u010dnih slu\u017ebenih\n           mjerenja (linija), 'band' crta dnevni raspon (sjena min\u2013maks + linija zadnjeg\n           mjerenja dana) iz akumuliranih dnevnih podataka. *\/\n        function waterMiniGraphHtml(rows, options) {\n            const opts = options || {};\n            const title = opts.title || '';\n            const mode = opts.mode || 'band'; \/* 'hourly' | 'dense' | 'band' *\/\n            const pointMode = mode !== 'band';\n            const limits = opts.limits || {};\n            const cleanRows = Array.isArray(rows)\n                ? rows.filter(row => row && Number.isFinite(Number(row.level_cm)))\n                : [];\n\n            const preparation = Number(limits && limits.preparation);\n            const hasPreparation = mode !== 'hourly' && Number.isFinite(preparation);\n            const thresholdHtml = hasPreparation\n                ? '<div class=\"mv-water-history-threshold\">Pripremno stanje: <strong>' + escapeHtml(fmt(preparation, 0)) + ' cm<\/strong><\/div>'\n                : '';\n\n            if (!cleanRows.length) {\n                return '<div class=\"mv-water-history-block is-' + mode + '\">' +\n                    '<div class=\"mv-water-history-head\"><span>' + escapeHtml(title) + '<\/span><\/div>' +\n                    '<div class=\"mv-water-history-empty\">Povijest se automatski prikuplja iz slu\u017ebenog izvora.<\/div>' +\n                    thresholdHtml + '<\/div>';\n            }\n\n            if (pointMode) {\n                cleanRows.sort((a, b) => Number(a.timestamp || 0) - Number(b.timestamp || 0));\n            }\n\n            const highs = cleanRows.map(row => mode === 'band' && Number.isFinite(Number(row.max_cm)) ? Number(row.max_cm) : Number(row.level_cm));\n            const lows  = cleanRows.map(row => mode === 'band' && Number.isFinite(Number(row.min_cm)) ? Number(row.min_cm) : Number(row.level_cm));\n            const observedMin = Math.min.apply(null, lows);\n            const observedMax = Math.max.apply(null, highs);\n            let min = observedMin;\n            let max = observedMax;\n            if (min === max) { min -= 1; max += 1; }\n\n            const observedSpan = Math.max(1, observedMax - observedMin);\n            const thresholdNearDistance = Math.max(40, observedSpan * 1.25);\n            const showPreparationLine = hasPreparation &&\n                preparation >= (observedMin - thresholdNearDistance) &&\n                preparation <= (observedMax + thresholdNearDistance);\n\n            if (showPreparationLine) {\n                min = Math.min(min, preparation);\n                max = Math.max(max, preparation);\n            }\n\n            const rawSpan = Math.max(1, max - min);\n            const pad = Math.max(2, rawSpan * 0.08);\n            min -= pad;\n            max += pad;\n\n            const W = 220, H = mode === 'band' ? 58 : 50, PX = 4, PY = 5;\n            const spanX = Math.max(1, W - PX * 2);\n            const spanY = Math.max(1, H - PY * 2);\n            const xForIndex = (i) => cleanRows.length === 1 ? W \/ 2 : PX + (i \/ (cleanRows.length - 1)) * spanX;\n            const yForValue = (value) => PY + ((max - Number(value)) \/ (max - min)) * spanY;\n\n            const points = cleanRows.map((row, i) => [xForIndex(i), yForValue(row.level_cm)]);\n            const linePoints = points.map(p => p[0].toFixed(1) + ',' + p[1].toFixed(1)).join(' ');\n            const last = points[points.length - 1];\n\n            let bandPolygon = '', areaPolygon = '';\n            if (mode === 'band') {\n                const topPts = cleanRows.map((row, i) => [xForIndex(i), yForValue(Number.isFinite(Number(row.max_cm)) ? row.max_cm : row.level_cm)]);\n                const botPts = cleanRows.map((row, i) => [xForIndex(i), yForValue(Number.isFinite(Number(row.min_cm)) ? row.min_cm : row.level_cm)]).reverse();\n                const bandPts = topPts.concat(botPts).map(p => p[0].toFixed(1) + ',' + p[1].toFixed(1)).join(' ');\n                bandPolygon = '<polygon class=\"mv-water-history-band\" points=\"' + bandPts + '\"><\/polygon>';\n            } else {\n                const areaPoints = PX + ',' + (H - PY) + ' ' + linePoints + ' ' + (W - PX) + ',' + (H - PY);\n                areaPolygon = '<polygon class=\"mv-water-history-area\" points=\"' + areaPoints + '\"><\/polygon>';\n            }\n\n            const firstLabel = mode === 'hourly' ? waterHourlyTimeLabel(cleanRows[0])\n                : mode === 'dense' ? waterHourlyDateTimeLabel(cleanRows[0])\n                : waterHistoryDateLabel(cleanRows[0].date);\n            const lastLabel = mode === 'hourly' ? waterHourlyTimeLabel(cleanRows[cleanRows.length - 1])\n                : mode === 'dense' ? waterHourlyDateTimeLabel(cleanRows[cleanRows.length - 1])\n                : waterHistoryDateLabel(cleanRows[cleanRows.length - 1].date);\n            const countLabel = mode === 'band'\n                ? (cleanRows.length >= 30 ? '30 dana' : cleanRows.length + (cleanRows.length === 1 ? ' dan' : ' dana'))\n                : cleanRows.length + (cleanRows.length === 1 ? ' mjerenje' : ' mjerenja');\n            const statsLabel = mode === 'band'\n                ? countLabel + ' \u00b7 raspon ' + escapeHtml(fmt(observedMin, 0)) + '\u2013' + escapeHtml(fmt(observedMax, 0)) + ' cm'\n                : countLabel + ' \u00b7 min ' + escapeHtml(fmt(observedMin, 0)) + ' \/ max ' + escapeHtml(fmt(observedMax, 0)) + ' cm';\n            const preparationLine = showPreparationLine\n                ? '<line class=\"mv-water-history-threshold-line\" x1=\"' + PX + '\" y1=\"' + yForValue(preparation).toFixed(1) + '\" x2=\"' + (W-PX) + '\" y2=\"' + yForValue(preparation).toFixed(1) + '\"><\/line>'\n                : '';\n\n            return '<div class=\"mv-water-history-block is-' + mode + '\">' +\n                '<div class=\"mv-water-history-head\"><span>' + escapeHtml(title) + '<\/span>' +\n                '<span class=\"mv-water-history-stats\">' + statsLabel + '<\/span><\/div>' +\n                '<svg class=\"mv-water-history-chart\" viewBox=\"0 0 ' + W + ' ' + H + '\" preserveAspectRatio=\"none\" aria-label=\"Kretanje vodostaja\">' +\n                '<line class=\"mv-water-history-grid\" x1=\"' + PX + '\" y1=\"' + (H\/2) + '\" x2=\"' + (W-PX) + '\" y2=\"' + (H\/2) + '\"><\/line>' +\n                preparationLine +\n                bandPolygon + areaPolygon +\n                '<polyline class=\"mv-water-history-line\" points=\"' + linePoints + '\"><\/polyline>' +\n                '<circle class=\"mv-water-history-dot\" cx=\"' + last[0].toFixed(1) + '\" cy=\"' + last[1].toFixed(1) + '\" r=\"2.8\"><\/circle>' +\n                '<\/svg>' +\n                '<div class=\"mv-water-history-dates\"><span>' + escapeHtml(firstLabel) + '<\/span><span>' + escapeHtml(lastLabel) + '<\/span><\/div>' +\n                thresholdHtml + '<\/div>';\n        }\n\n        \/* Isje\u010dak niza za odabrani raspon. 24h\/3d\/7d prednost daju gustoj povijesti (history_7d,\n           svako slu\u017ebeno mjerenje do 8 dana); 14d\/30d koriste dnevni raspon (history_30d, band).\n           Ako gusta povijest jo\u0161 nije prikupljena (netom nakon nadogradnje), 3d\/7d se oslanjaju\n           na dnevni prikaz kako graf ne bi ostao prazan. *\/\n        const WATER_RANGES = {\n            '24h': {days: 1,  hours: 24,   label: '24 SATA',    trendLabel: 'U zadnja 24 h',      graphTitle: 'GRAF \u00b7 24 SATA',   shortLabel: '24 sata',   agoLabel: 'Prije 24 h'},\n            '3d':  {days: 3,  hours: 72,   label: '3 DANA',     trendLabel: 'U zadnja 3 dana',    graphTitle: 'GRAF \u00b7 3 DANA',    shortLabel: '3 dana',    agoLabel: 'Prije 3 dana'},\n            '7d':  {days: 7,  hours: 168,  label: '7 DANA',     trendLabel: 'U zadnjih 7 dana',   graphTitle: 'GRAF \u00b7 7 DANA',   shortLabel: '7 dana',    agoLabel: 'Prije 7 dana'},\n            '14d': {days: 14, hours: 336,  label: '14 DANA',    trendLabel: 'U zadnjih 14 dana',  graphTitle: 'GRAF \u00b7 14 DANA \u00b7 DNEVNI RASPON',     shortLabel: '14 dana',   agoLabel: 'Prije 14 dana'},\n            '30d': {days: 30, hours: 720,  label: '30 DANA',    trendLabel: 'U zadnjih 30 dana',  graphTitle: 'GRAF \u00b7 30 DANA \u00b7 DNEVNI RASPON',     shortLabel: '30 dana',   agoLabel: 'Prije 30 dana'}\n        };\n\n        const WATER_CHANGE_ROWS = ['24h','3d','7d','30d'];\n\n        function waterGraphForRange(station, range) {\n            const cfg = WATER_RANGES[range] || WATER_RANGES['24h'];\n            if (range === '24h') {\n                return {mode:'hourly', rows: station && station.history_24h, title: cfg.graphTitle};\n            }\n            const dense = Array.isArray(station && station.history_7d) ? station.history_7d : [];\n            if (range === '3d' || range === '7d') {\n                const cutoff = Date.now() \/ 1000 - cfg.hours * 3600;\n                const rows = dense.filter(r => Number(r && r.timestamp) >= cutoff);\n                if (rows.length >= 4) return {mode:'dense', rows, title: cfg.graphTitle};\n                \/* Nema jo\u0161 dovoljno guste povijesti \u2013 graf privremeno pada natrag na dnevni raspon. *\/\n                const daily = (Array.isArray(station && station.history_30d) ? station.history_30d : []).slice(-cfg.days);\n                return {mode:'band', rows: daily, title: cfg.graphTitle + ' \u00b7 DNEVNI RASPON'};\n            }\n            const daily = (Array.isArray(station && station.history_30d) ? station.history_30d : []).slice(-cfg.days);\n            return {mode:'band', rows: daily, title: cfg.graphTitle};\n        }\n\n        function renderWaterHistory(stationKey, station, range) {\n            const el = qs('water-' + stationKey + '-history');\n            if (!el) return;\n            const graph = waterGraphForRange(station, range);\n            el.innerHTML = waterMiniGraphHtml(graph.rows, {title: graph.title, mode: graph.mode, limits: (station && station.limits) || {}});\n        }\n\n\n\n        function formatClock(value) {\n            const d = value ? new Date(value) : new Date();\n            if (Number.isNaN(d.getTime())) return '\u2014';\n            return d.toLocaleTimeString('hr-HR', {hour:'2-digit', minute:'2-digit', second:'2-digit'});\n        }\n\n        function updateDubrovacakClock() {\n            const el = qs('dub-live-clock');\n            if (el) el.textContent = formatClock(new Date());\n        }\n\n        function dubrovacakAirTemperature(data) {\n            const list = Array.isArray(data?.places) ? data.places : [];\n            const place = list.find(item => String(item?.name || '').toLowerCase().includes('dubrov\u010dak'));\n            const value = Number(place?.current?.temperature_2m);\n            if (Number.isFinite(value)) return value;\n            const fallback = Number(data?.forecast?.current?.temperature_2m);\n            return Number.isFinite(fallback) ? fallback : null;\n        }\n\n        \/* Pragovi obrane od poplava koji upadaju u (pro\u0161ireni) vidljivi raspon grafa \u2013 isti\n           test blizine kao kod trake pragova na glavnim karticama Save, samo ovdje mogu biti\n           prikazana i vi\u0161e od jednog praga odjednom (ovo je \"detaljni\" prikaz). *\/\n        function detailedWaterVisibleThresholds(limits, min, max) {\n            const stages = [\n                {key:'preparation',   label:'Pripremno stanje',   color:'#d4a017'},\n                {key:'regular',       label:'Redovne mjere',      color:'#ef8b2c'},\n                {key:'extraordinary', label:'Izvanredne mjere',   color:'#dd5a32'},\n                {key:'emergency',     label:'Izvanredno stanje',  color:'#c62f38'}\n            ];\n            const span = Math.max(1, max - min);\n            const nearDistance = Math.max(50, span * 0.35);\n            return stages\n                .map(s => Object.assign({}, s, {value: Number(limits && limits[s.key])}))\n                .filter(s => Number.isFinite(s.value) && s.value >= (min - nearDistance) && s.value <= (max + nearDistance));\n        }\n\n        function detailedWaterChartHtml(rows, options) {\n            const opts = options || {};\n            const title = opts.title || '';\n            const subtitle = opts.subtitle || '';\n            const mode = opts.mode || 'time';\n            const band = !!opts.band;\n            const limits = opts.limits || {};\n            \/* Na uskom zaslonu SVG se smanjuje razmjerno \u0161irini kartice, pa bi tekst u istim\n               \"viewBox\" jedinicama postao sitan i ne\u010ditljiv (isti fiksni viewBox koristi se na\n               svim \u0161irinama). fs() kompenzira tu razliku umjesto da tekst bude \u010ditljiv samo na\n               desktopu. *\/\n            const isNarrow = typeof window !== 'undefined' && window.innerWidth <= 650;\n            const fs = base => isNarrow ? Math.round(base * 3) : base;\n            const clean = (Array.isArray(rows) ? rows : [])\n                .filter(row => row && Number.isFinite(Number(row.level_cm)))\n                .map(row => Object.assign({}, row, {\n                    level_cm:Number(row.level_cm),\n                    min_cm:Number.isFinite(Number(row.min_cm)) ? Number(row.min_cm) : Number(row.level_cm),\n                    max_cm:Number.isFinite(Number(row.max_cm)) ? Number(row.max_cm) : Number(row.level_cm),\n                    timestamp:Number(row.timestamp || 0)\n                }))\n                .sort((a,b) => a.timestamp - b.timestamp);\n\n            if (!clean.length) {\n                return '<div class=\"mv-dub-chart-head\"><div><div class=\"mv-dub-chart-title\">' + escapeHtml(title) + '<\/div><\/div><\/div>' +\n                    '<div class=\"mv-dub-chart-empty\">Podaci \u0107e se pojaviti \u010dim se prikupi prvo slu\u017ebeno mjerenje za ovo razdoblje.<\/div>';\n            }\n\n            const lows = clean.map(row => band ? row.min_cm : row.level_cm);\n            const highs = clean.map(row => band ? row.max_cm : row.level_cm);\n            const observedMin = Math.min.apply(null, lows);\n            const observedMax = Math.max.apply(null, highs);\n            let min = observedMin, max = observedMax;\n            if (min === max) { min -= 1; max += 1; }\n            const pad = Math.max(1.5, (max - min) * 0.12);\n            min -= pad; max += pad;\n\n            const thresholds = detailedWaterVisibleThresholds(limits, min, max);\n            thresholds.forEach(t => { min = Math.min(min, t.value); max = Math.max(max, t.value); });\n            if (thresholds.length) { const p2 = (max-min)*0.06; min -= p2; max += p2; }\n\n            const W = 1000, H = isNarrow ? 520 : 230;\n            const L = isNarrow ? 110 : 62, R = 18, T = 22, B = isNarrow ? 70 : 36;\n            const plotW = W - L - R, plotH = H - T - B;\n            const firstTs = clean[0].timestamp || 0;\n            const lastTs = clean[clean.length - 1].timestamp || firstTs;\n            const spanTs = Math.max(1, lastTs - firstTs);\n\n            const xFor = (row, i) => {\n                if (clean.length === 1 || !row.timestamp) return L + (clean.length === 1 ? plotW\/2 : (i\/(clean.length-1))*plotW);\n                return L + ((row.timestamp - firstTs) \/ spanTs) * plotW;\n            };\n            const yFor = value => T + ((max - Number(value)) \/ (max - min)) * plotH;\n\n            const pts = clean.map((row,i) => [xFor(row,i), yFor(row.level_cm)]);\n            const poly = pts.map(p => p[0].toFixed(1)+','+p[1].toFixed(1)).join(' ');\n            const area = L+','+(H-B)+' '+poly+' '+(W-R)+','+(H-B);\n\n            let bandPolygon = '';\n            if (band) {\n                const topPts = clean.map((row,i) => [xFor(row,i), yFor(row.max_cm)]);\n                const botPts = clean.map((row,i) => [xFor(row,i), yFor(row.min_cm)]).reverse();\n                const bandPts = topPts.concat(botPts).map(p => p[0].toFixed(1)+','+p[1].toFixed(1)).join(' ');\n                bandPolygon = '<polygon class=\"mv-dub-chart-band\" points=\"'+bandPts+'\"><\/polygon>';\n            }\n\n            let grid = '';\n            for (let i=0; i<5; i++) {\n                const ratio = i\/4;\n                const y = T + ratio*plotH;\n                const val = max - ratio*(max-min);\n                grid += '<line x1=\"'+L+'\" y1=\"'+y.toFixed(1)+'\" x2=\"'+(W-R)+'\" y2=\"'+y.toFixed(1)+'\" stroke=\"#e8eef4\" stroke-width=\"1\"><\/line>';\n                grid += '<text x=\"'+(L-9)+'\" y=\"'+(y+4).toFixed(1)+'\" text-anchor=\"end\" font-size=\"'+fs(11)+'\" fill=\"#8191a1\">'+escapeHtml(fmt(val,0))+'<\/text>';\n            }\n\n            let thresholdLines = '', thresholdLabels = '';\n            thresholds.forEach(t => {\n                const y = yFor(t.value).toFixed(1);\n                thresholdLines += '<line class=\"mv-dub-chart-threshold\" x1=\"'+L+'\" y1=\"'+y+'\" x2=\"'+(W-R)+'\" y2=\"'+y+'\" stroke=\"'+t.color+'\"><\/line>';\n                thresholdLabels += '<text x=\"'+(W-R-4)+'\" y=\"'+(Number(y)-4-(isNarrow?6:0)).toFixed(1)+'\" text-anchor=\"end\" font-size=\"'+fs(10)+'\" font-weight=\"700\" fill=\"'+t.color+'\" stroke=\"#fff\" stroke-width=\"4\" paint-order=\"stroke\">'+escapeHtml((isNarrow ? t.label.replace('stanje','st.').replace('mjere','mj.') : t.label)+' '+fmt(t.value,0)+' cm')+'<\/text>';\n            });\n\n            let xlabels = '';\n            const ticks = Math.min(5, clean.length);\n            for (let i=0; i<ticks; i++) {\n                const idx = ticks === 1 ? 0 : Math.round((i\/(ticks-1))*(clean.length-1));\n                const row = clean[idx];\n                const x = xFor(row, idx);\n                let label = '';\n                if (mode === 'day') {\n                    label = waterHistoryDateLabel(row.date || '');\n                } else if (row.timestamp) {\n                    const d = new Date(row.timestamp * 1000);\n                    label = mode === 'week'\n                        ? d.toLocaleString('hr-HR',{day:'2-digit',month:'2-digit',hour:'2-digit'})\n                        : d.toLocaleTimeString('hr-HR',{hour:'2-digit',minute:'2-digit'});\n                }\n                xlabels += '<text x=\"'+x.toFixed(1)+'\" y=\"'+(H-10)+'\" text-anchor=\"'+(i===0?'start':(i===ticks-1?'end':'middle'))+'\" font-size=\"'+fs(10)+'\" fill=\"#8b9aaa\">'+escapeHtml(label)+'<\/text>';\n            }\n\n            const first = pts[0];\n            const last = pts[pts.length-1];\n            let endpointMarks = '';\n            if (opts.showEndpoints && clean.length >= 2) {\n                const firstY = Math.max(T + 12, first[1] - 9);\n                const lastY = Math.max(T + 12, last[1] - 9);\n                endpointMarks =\n                    '<circle cx=\"'+first[0].toFixed(1)+'\" cy=\"'+first[1].toFixed(1)+'\" r=\"4\" fill=\"#2e74bd\"><\/circle>' +\n                    '<text x=\"'+(first[0]+7).toFixed(1)+'\" y=\"'+firstY.toFixed(1)+'\" text-anchor=\"start\" font-size=\"'+fs(11)+'\" font-weight=\"700\" fill=\"#173f73\">'+escapeHtml(fmt(clean[0].level_cm,0))+' cm<\/text>' +\n                    '<text x=\"'+(last[0]-7).toFixed(1)+'\" y=\"'+lastY.toFixed(1)+'\" text-anchor=\"end\" font-size=\"'+fs(11)+'\" font-weight=\"700\" fill=\"#173f73\">'+escapeHtml(fmt(clean[clean.length-1].level_cm,0))+' cm<\/text>';\n            }\n            const countText = clean.length + (clean.length === 1 ? ' mjerenje' : ' mjerenja');\n            const stats = band\n                ? countText + ' \u00b7 dnevni raspon ' + fmt(observedMin,0) + '\u2013' + fmt(observedMax,0) + ' cm'\n                : countText + ' \u00b7 min ' + fmt(observedMin,0) + ' \/ max ' + fmt(observedMax,0) + ' cm';\n\n            return '<div class=\"mv-dub-chart-head\">' +\n                    '<div><div class=\"mv-dub-chart-title\">'+escapeHtml(title)+'<\/div>' +\n                    (subtitle ? '<div class=\"mv-dub-detail-subtitle\">'+escapeHtml(subtitle)+'<\/div>' : '') +\n                    '<\/div><div class=\"mv-dub-chart-stats\">'+escapeHtml(stats)+'<\/div><\/div>' +\n                '<svg class=\"mv-dub-chart-svg\" viewBox=\"0 0 '+W+' '+H+'\" role=\"img\" aria-label=\"'+escapeHtml(title)+'\">' +\n                    grid +\n                    thresholdLines +\n                    bandPolygon +\n                    (band ? '' : '<polygon points=\"'+area+'\" fill=\"#2e74bd\" opacity=\".07\"><\/polygon>') +\n                    '<polyline points=\"'+poly+'\" fill=\"none\" stroke=\"#2e74bd\" stroke-width=\"2.5\" stroke-linecap=\"round\" stroke-linejoin=\"round\" vector-effect=\"non-scaling-stroke\"><\/polyline>' +\n                    thresholdLabels +\n                    endpointMarks +\n                    '<circle cx=\"'+last[0].toFixed(1)+'\" cy=\"'+last[1].toFixed(1)+'\" r=\"4.2\" fill=\"#2e74bd\"><\/circle>' +\n                    xlabels +\n                    '<text x=\"18\" y=\"'+(T+plotH\/2).toFixed(1)+'\" transform=\"rotate(-90 18 '+(T+plotH\/2).toFixed(1)+')\" text-anchor=\"middle\" font-size=\"'+fs(10)+'\" fill=\"#8b9aaa\">cm<\/text>' +\n                '<\/svg>';\n        }\n\n        function dubrovacakHistoryRows(station) {\n            const primary = Array.isArray(station?.history_7d) && station.history_7d.length\n                ? station.history_7d\n                : (Array.isArray(station?.history_24h) ? station.history_24h : []);\n            return primary.filter(row => row && Number.isFinite(Number(row.level_cm)) && Number(row.timestamp || 0) > 0)\n                .map(row => Object.assign({}, row, {level_cm:Number(row.level_cm),timestamp:Number(row.timestamp)}))\n                .sort((a,b) => a.timestamp - b.timestamp);\n        }\n\n        function dubrovacakPointNear(rows, targetTs, toleranceSeconds) {\n            let best = null, bestDiff = Infinity;\n            (Array.isArray(rows) ? rows : []).forEach(row => {\n                const ts = Number(row?.timestamp || 0);\n                if (!ts) return;\n                const diff = Math.abs(ts - targetTs);\n                if (diff < bestDiff) { best = row; bestDiff = diff; }\n            });\n            return best && bestDiff <= toleranceSeconds ? best : null;\n        }\n\n        function dubrovacak24hSummaryHtml(station, range) {\n            const cfg = WATER_RANGES[range] || WATER_RANGES['24h'];\n            \/* Svi izvori (satni, gusti do 8 dana, dnevni do 30 dana) \u2013 isto kao retci promjene\n               na glavnim karticama, pa i \"Prije 30 dana\" ima podatak. *\/\n            const rows = waterHistoryPoints(station).map(p => ({timestamp: p.ts\/1000, level_cm: p.level}));\n            if (!rows.length) return '';\n            const latest = rows[rows.length - 1];\n            const previous = dubrovacakPointNear(rows.filter(r => r.timestamp < latest.timestamp - 600), latest.timestamp - cfg.hours*3600, waterRangeTolerance(range)*3600);\n            const change = previous ? latest.level_cm - previous.level_cm : null;\n            const changeClass = Number.isFinite(change) ? (change > 0 ? 'is-up' : change < 0 ? 'is-down' : '') : '';\n            const changeArrow = Number.isFinite(change) ? (change > 0 ? '\u2191 ' : change < 0 ? '\u2193 ' : '\u2192 ') : '';\n            const dtLabel = row => {\n                if (!row || !row.timestamp) return '\u2014';\n                return new Date(row.timestamp*1000).toLocaleString('hr-HR',{day:'2-digit',month:'2-digit',hour:'2-digit',minute:'2-digit'});\n            };\n            return '<div class=\"mv-dub-24h-summary-item\">' +\n                    '<span class=\"mv-dub-24h-summary-label\">'+escapeHtml(cfg.agoLabel)+'<\/span>' +\n                    '<strong class=\"mv-dub-24h-summary-value\">'+(previous ? escapeHtml(fmt(previous.level_cm,0))+' cm' : '\u2014')+'<\/strong>' +\n                    '<span class=\"mv-dub-24h-summary-time\">'+escapeHtml(dtLabel(previous))+'<\/span>' +\n                '<\/div>' +\n                '<div class=\"mv-dub-24h-summary-item\">' +\n                    '<span class=\"mv-dub-24h-summary-label\">Sada<\/span>' +\n                    '<strong class=\"mv-dub-24h-summary-value\">'+escapeHtml(fmt(latest.level_cm,0))+' cm<\/strong>' +\n                    '<span class=\"mv-dub-24h-summary-time\">'+escapeHtml(dtLabel(latest))+'<\/span>' +\n                '<\/div>' +\n                '<div class=\"mv-dub-24h-summary-item is-change\">' +\n                    '<span class=\"mv-dub-24h-summary-label\">'+escapeHtml(cfg.trendLabel)+'<\/span>' +\n                    '<strong class=\"mv-dub-24h-summary-value '+changeClass+'\">'+(Number.isFinite(change) ? changeArrow + (change > 0 ? '+' : '') + escapeHtml(fmt(change,0)) + ' cm' : '\u2014')+'<\/strong>' +\n                    '<span class=\"mv-dub-24h-summary-time\">stvarna mjerenja \u00b7 nije prognoza<\/span>' +\n                '<\/div>';\n        }\n\n        function detailedWaterBarChartHtml(rows, options) {\n            const opts = options || {};\n            const title = opts.title || 'Promjena vodostaja';\n            const subtitle = opts.subtitle || '';\n            const isNarrow = typeof window !== 'undefined' && window.innerWidth <= 650;\n            const fs = base => isNarrow ? Math.round(base * 3) : base;\n            const clean = (Array.isArray(rows) ? rows : [])\n                .filter(row => row && Number.isFinite(Number(row.level_cm)) && Number(row.timestamp || 0) > 0)\n                .map(row => Object.assign({}, row, {level_cm:Number(row.level_cm),timestamp:Number(row.timestamp)}))\n                .sort((a,b) => a.timestamp - b.timestamp);\n\n            if (clean.length < 2) {\n                return '<div class=\"mv-dub-chart-head\"><div><div class=\"mv-dub-chart-title\">'+escapeHtml(title)+'<\/div><\/div><\/div>' +\n                    '<div class=\"mv-dub-chart-empty\">Za stup\u010dasti prikaz potrebna su najmanje dva slu\u017ebena mjerenja.<\/div>';\n            }\n\n            const spanH = (clean[clean.length-1].timestamp - clean[0].timestamp) \/ 3600;\n            const tLabel = ts => {\n                const d = new Date(ts*1000);\n                if (spanH > 180) return d.toLocaleDateString('hr-HR',{day:'2-digit',month:'2-digit'});\n                if (spanH > 36) return d.toLocaleString('hr-HR',{day:'2-digit',month:'2-digit',hour:'2-digit'});\n                return d.toLocaleTimeString('hr-HR',{hour:'2-digit',minute:'2-digit'});\n            };\n            const changes = [];\n            for (let i=1; i<clean.length; i++) {\n                const delta = clean[i].level_cm - clean[i-1].level_cm;\n                changes.push({\n                    timestamp:clean[i].timestamp,\n                    delta,\n                    from:clean[i-1].level_cm,\n                    to:clean[i].level_cm,\n                    dt:clean[i].timestamp-clean[i-1].timestamp\n                });\n            }\n\n            const values = changes.map(r => r.delta);\n            let min = Math.min(0, ...values), max = Math.max(0, ...values);\n            if (min === max) { min -= 1; max += 1; }\n            const pad = Math.max(1, (max-min)*0.10);\n            if (min < 0) min -= pad;\n            if (max > 0) max += pad;\n\n            const W=1000,H=isNarrow?460:230,L=isNarrow?110:62,R=18,T=22,B=isNarrow?70:36;\n            const plotW=W-L-R, plotH=H-T-B;\n            const yFor = v => T + ((max-Number(v))\/(max-min))*plotH;\n            const zeroY = yFor(0);\n            const step = plotW \/ Math.max(1,changes.length);\n            const barW = Math.max(5,Math.min(30,step*0.62));\n\n            let grid = '<line x1=\"'+L+'\" y1=\"'+zeroY.toFixed(1)+'\" x2=\"'+(W-R)+'\" y2=\"'+zeroY.toFixed(1)+'\" stroke=\"#aebdca\" stroke-width=\"1.3\"><\/line>' +\n                '<text x=\"'+(L-9)+'\" y=\"'+(zeroY+4).toFixed(1)+'\" text-anchor=\"end\" font-size=\"'+fs(11)+'\" fill=\"#8191a1\">0<\/text>';\n            [min,max].forEach(v => {\n                if (Math.abs(v) < 0.001) return;\n                const y=yFor(v);\n                grid += '<line x1=\"'+L+'\" y1=\"'+y.toFixed(1)+'\" x2=\"'+(W-R)+'\" y2=\"'+y.toFixed(1)+'\" stroke=\"#e8eef4\" stroke-width=\"1\"><\/line>' +\n                    '<text x=\"'+(L-9)+'\" y=\"'+(y+4).toFixed(1)+'\" text-anchor=\"end\" font-size=\"'+fs(11)+'\" fill=\"#8191a1\">'+escapeHtml(fmt(v,0))+'<\/text>';\n            });\n\n            let bars='';\n            changes.forEach((row,i) => {\n                const x=L+i*step+(step-barW)\/2;\n                const y=yFor(row.delta);\n                const top=Math.min(y,zeroY), height=Math.max(1,Math.abs(zeroY-y));\n                const fill=row.delta>0?'#d96e16':row.delta<0?'#2678ad':'#9aaab7';\n                const time=tLabel(row.timestamp);\n                const sign=row.delta>0?'+':'';\n                bars += '<rect x=\"'+x.toFixed(1)+'\" y=\"'+top.toFixed(1)+'\" width=\"'+barW.toFixed(1)+'\" height=\"'+height.toFixed(1)+'\" rx=\"2\" fill=\"'+fill+'\" opacity=\".88\">' +\n                    '<title>'+escapeHtml(time+' \u00b7 '+sign+fmt(row.delta,0)+' cm \u00b7 '+fmt(row.from,0)+' \u2192 '+fmt(row.to,0)+' cm')+'<\/title><\/rect>';\n            });\n\n            let xlabels='';\n            const ticks=Math.min(5,changes.length);\n            for(let i=0;i<ticks;i++){\n                const idx=ticks===1?0:Math.round((i\/(ticks-1))*(changes.length-1));\n                const row=changes[idx];\n                const x=L+idx*step+step\/2;\n                const label=tLabel(row.timestamp);\n                xlabels += '<text x=\"'+x.toFixed(1)+'\" y=\"'+(H-10)+'\" text-anchor=\"'+(i===0?'start':(i===ticks-1?'end':'middle'))+'\" font-size=\"'+fs(10)+'\" fill=\"#8b9aaa\">'+escapeHtml(label)+'<\/text>';\n            }\n\n            const maxRise=Math.max(...values), maxFall=Math.min(...values);\n            const stats='najve\u0107i rast '+(maxRise>0?'+':'')+fmt(maxRise,0)+' cm \u00b7 najve\u0107i pad '+fmt(maxFall,0)+' cm';\n            return '<div class=\"mv-dub-chart-head\">' +\n                    '<div><div class=\"mv-dub-chart-title\">'+escapeHtml(title)+'<\/div>' +\n                    (subtitle?'<div class=\"mv-dub-detail-subtitle\">'+escapeHtml(subtitle)+'<\/div>':'') +\n                    '<\/div><div class=\"mv-dub-chart-stats\">'+escapeHtml(stats)+'<\/div><\/div>' +\n                '<svg class=\"mv-dub-chart-svg\" viewBox=\"0 0 '+W+' '+H+'\" role=\"img\" aria-label=\"'+escapeHtml(title)+'\">' +\n                    grid+bars+xlabels+\n                    '<text x=\"18\" y=\"'+(T+plotH\/2).toFixed(1)+'\" transform=\"rotate(-90 18 '+(T+plotH\/2).toFixed(1)+')\" text-anchor=\"middle\" font-size=\"'+fs(10)+'\" fill=\"#8b9aaa\">cm<\/text>' +\n                '<\/svg>';\n        }\n\n        function dubrovacakCrossSectionHtml(station) {\n            if (!station || !station.ok || !Number.isFinite(Number(station.level_cm))) {\n                return '<div class=\"mv-dub-chart-empty\">Slu\u017ebeni vodostaj trenuta\u010dno nije dostupan.<\/div>';\n            }\n\n            const level = Number(station.level_cm);\n            const limits = station.limits || {};\n            const prep = Number(limits.preparation);\n            const regular = Number(limits.regular);\n            const extraordinary = Number(limits.extraordinary);\n            const emergency = Number(limits.emergency);\n            const limitValues = [prep,regular,extraordinary,emergency].filter(Number.isFinite);\n            const maxLimit = limitValues.length ? Math.max.apply(null, limitValues) : level + 500;\n            const minScale = Math.min(level - 120, 0);\n            const maxScale = Math.max(maxLimit + 70, level + 120);\n            const W = 1000, H = 360, top = 24, bottom = 326;\n            const plotH = bottom - top;\n            const yFor = value => top + ((maxScale - Number(value)) \/ (maxScale - minScale)) * plotH;\n            const currentY = yFor(level);\n            const isMobileCross = (typeof window !== 'undefined' && window.innerWidth <= 650);\n            const badgeX = isMobileCross ? 24 : 105;\n            const badgeWidth = isMobileCross ? 390 : 195;\n            const badgeHeight = isMobileCross ? 86 : 38;\n            \/* Na mobitelu se SVG smanjuje na ~1\/3 \u0161irine, pa tekst u presjeku mora biti\n               razmjerno ve\u0107i da ostane \u010ditljiv. *\/\n            const crossFs = base => isMobileCross ? Math.round(base * 2.4) : base;\n            const badgeRadius = badgeHeight \/ 2;\n            const badgeCenterX = badgeX + badgeWidth \/ 2;\n            const badgeTop = currentY - badgeHeight \/ 2;\n            const currentTextY = currentY - (isMobileCross ? 6 : 4);\n            const currentSubtextY = currentY + (isMobileCross ? 26 : 10);\n            const thresholdRectX = isMobileCross ? 628 : 650;\n            const thresholdRectWidth = isMobileCross ? 284 : 258;\n            const thresholdRectHeight = isMobileCross ? 30 : 26;\n            const thresholdRectRadius = thresholdRectHeight \/ 2;\n\n            const lines = [\n                {v:prep, label:'Pripremno stanje', cls:'#d4a017'},\n                {v:regular, label:'Redovne mjere', cls:'#ef8b2c'},\n                {v:extraordinary, label:'Izvanredne mjere', cls:'#dd5a32'},\n                {v:emergency, label:'Izvanredno stanje', cls:'#c62f38'}\n            ].filter(item => Number.isFinite(item.v));\n\n            let thresholds = '';\n            lines.forEach(item => {\n                const y = yFor(item.v);\n                thresholds += '<line x1=\"40\" y1=\"'+y.toFixed(1)+'\" x2=\"960\" y2=\"'+y.toFixed(1)+'\" stroke=\"'+item.cls+'\" stroke-width=\"1.6\" stroke-dasharray=\"6 5\" opacity=\".9\"><\/line>' +\n                    '<text class=\"mv-dub-cross-threshold-text\" x=\"960\" y=\"'+(y-(isMobileCross?9:7)).toFixed(1)+'\" text-anchor=\"end\" font-size=\"'+crossFs(11)+'\" font-weight=\"700\" fill=\"'+item.cls+'\" stroke=\"#f9fcfe\" stroke-width=\"'+(isMobileCross?8:5)+'\" paint-order=\"stroke\">'+escapeHtml(isMobileCross ? item.label.replace('stanje','st.').replace('mjere','mj.') : item.label)+' \u00b7 '+escapeHtml(fmt(item.v,0))+' cm<\/text>';\n            });\n\n            const secondary = station.secondary && station.secondary.ok && Number.isFinite(Number(station.secondary.level_cm))\n                ? Number(station.secondary.level_cm) : null;\n            let secondaryLine = '';\n            if (secondary !== null && Math.abs(secondary - level) > 0.01) {\n                const y2 = yFor(secondary);\n                secondaryLine = '<line x1=\"120\" y1=\"'+y2.toFixed(1)+'\" x2=\"690\" y2=\"'+y2.toFixed(1)+'\" stroke=\"#6e7f90\" stroke-width=\"1.5\" stroke-dasharray=\"4 4\"><\/line>' +\n                    '<text x=\"128\" y=\"'+(y2-7).toFixed(1)+'\" font-size=\"'+crossFs(11)+'\" fill=\"#5f7182\">DHMZ '+escapeHtml(fmt(secondary,0))+' cm<\/text>';\n            }\n\n            const waterTop = Math.min(bottom-5, Math.max(top+5, currentY));\n            const prepGap = Number.isFinite(prep) ? prep - level : null;\n            const prepContext = prepGap === null ? ''\n                : prepGap > 0 ? fmt(prepGap,0) + ' cm ispod pripremnog stanja'\n                : prepGap < 0 ? fmt(Math.abs(prepGap),0) + ' cm iznad pripremnog stanja'\n                : 'Na pragu pripremnog stanja';\n            return '<svg class=\"mv-dub-cross-svg\" viewBox=\"0 0 '+W+' '+H+'\" role=\"img\" aria-label=\"Shematski presjek korita Save kod Dubrov\u010daka\">' +\n                '<defs>' +\n                    '<clipPath id=\"mvDubChannel\"><path d=\"M0 0 L0 88 C145 102 215 142 298 235 C356 300 410 325 500 329 C590 325 644 300 702 235 C785 142 855 102 1000 88 L1000 0 Z\"><\/path><\/clipPath>' +\n                    '<linearGradient id=\"mvDubWater\" x1=\"0\" y1=\"0\" x2=\"0\" y2=\"1\"><stop offset=\"0\" stop-color=\"#7fb8e3\"><\/stop><stop offset=\"1\" stop-color=\"#2f78b5\"><\/stop><\/linearGradient>' +\n                    '<linearGradient id=\"mvDubBank\" x1=\"0\" y1=\"0\" x2=\"0\" y2=\"1\"><stop offset=\"0\" stop-color=\"#ece4d8\"><\/stop><stop offset=\"1\" stop-color=\"#d9ccb9\"><\/stop><\/linearGradient>' +\n                '<\/defs>' +\n                '<rect width=\"'+W+'\" height=\"'+H+'\" fill=\"#f9fcfe\"><\/rect>' +\n                '<path d=\"M0 88 C145 102 215 142 298 235 C356 300 410 325 500 329 C590 325 644 300 702 235 C785 142 855 102 1000 88 L1000 360 L0 360 Z\" fill=\"url(#mvDubBank)\"><\/path>' +\n                '<path d=\"M0 88 C145 102 215 142 298 235 C356 300 410 325 500 329 L0 360 Z\" fill=\"url(#mvDubBank)\"><\/path>' +\n                '<path d=\"M1000 88 C855 102 785 142 702 235 C644 300 590 325 500 329 L1000 360 Z\" fill=\"url(#mvDubBank)\"><\/path>' +\n                '<path d=\"M0 88 C145 102 215 142 298 235 C356 300 410 325 500 329 C590 325 644 300 702 235 C785 142 855 102 1000 88\" fill=\"none\" stroke=\"#b8a995\" stroke-width=\"3\"><\/path>' +\n                '<rect x=\"0\" y=\"'+waterTop.toFixed(1)+'\" width=\"'+W+'\" height=\"'+(H-waterTop).toFixed(1)+'\" fill=\"url(#mvDubWater)\" opacity=\".85\" clip-path=\"url(#mvDubChannel)\"><\/rect>' +\n                thresholds +\n                secondaryLine +\n                '<line x1=\"0\" y1=\"'+currentY.toFixed(1)+'\" x2=\"'+W+'\" y2=\"'+currentY.toFixed(1)+'\" stroke=\"#0b3d78\" stroke-width=\"3\" clip-path=\"url(#mvDubChannel)\"><\/line>' +\n                '<circle cx=\"500\" cy=\"'+currentY.toFixed(1)+'\" r=\"6\" fill=\"#0b3d78\"><\/circle>' +\n                '<rect x=\"'+badgeX+'\" y=\"'+badgeTop.toFixed(1)+'\" width=\"'+badgeWidth+'\" height=\"'+badgeHeight+'\" rx=\"'+badgeRadius+'\" fill=\"#0b3d78\"><\/rect>' +\n                '<text class=\"mv-dub-cross-current-text\" x=\"'+badgeCenterX+'\" y=\"'+currentTextY.toFixed(1)+'\" text-anchor=\"middle\" font-size=\"'+crossFs(12.5)+'\" font-weight=\"700\" fill=\"#fff\">Trenutno '+escapeHtml(fmt(level,0))+' cm<\/text>' +\n                (prepContext ? '<text class=\"mv-dub-cross-current-subtext\" x=\"'+badgeCenterX+'\" y=\"'+currentSubtextY.toFixed(1)+'\" text-anchor=\"middle\" font-size=\"'+(isMobileCross?19:8.5)+'\" font-weight=\"600\" fill=\"#dbeeff\">'+escapeHtml(prepContext)+'<\/text>' : '') +\n                '<text x=\"500\" y=\"350\" text-anchor=\"middle\" font-size=\"'+crossFs(10)+'\" fill=\"#8c7c66\">SHEMATSKI PRIKAZ \u00b7 NIJE GEODETSKI PRESJEK<\/text>' +\n                '<\/svg>' +\n                '<div class=\"mv-dub-cross-legend\">' +\n                    '<span><i class=\"mv-dub-legend-line\"><\/i>Trenutni vodostaj<\/span>' +\n                    '<span><i class=\"mv-dub-legend-line prep\"><\/i>Pripremno<\/span>' +\n                    '<span><i class=\"mv-dub-legend-line regular\"><\/i>Redovne mjere<\/span>' +\n                    '<span><i class=\"mv-dub-legend-line extra\"><\/i>Izvanredne mjere<\/span>' +\n                    '<span><i class=\"mv-dub-legend-line emergency\"><\/i>Izvanredno stanje<\/span>' +\n                '<\/div>';\n        }\n\n        function dubrovacakRateStats(station) {\n            const source = Array.isArray(station?.history_7d) && station.history_7d.length >= 2\n                ? station.history_7d\n                : (Array.isArray(station?.history_24h) ? station.history_24h : []);\n\n            const points = source.map(row => ({\n                ts: Number(row?.timestamp || 0) * 1000,\n                level: Number(row?.level_cm)\n            })).filter(p => Number.isFinite(p.ts) && p.ts > 0 && Number.isFinite(p.level))\n              .sort((a,b) => a.ts - b.ts);\n\n            if (points.length < 2) {\n                return {prefix:'Trend', minute:null, hour:null, day:null};\n            }\n\n            const latest = points[points.length - 1];\n            const previous = points[points.length - 2];\n            const dtMinutes = (latest.ts - previous.ts) \/ 60000;\n            const minute = dtMinutes > 0 ? (latest.level - previous.level) \/ dtMinutes : null;\n\n            function deltaNear(seconds, toleranceSeconds) {\n                const target = latest.ts - seconds * 1000;\n                let best = null;\n                let bestDiff = Infinity;\n                for (let i = 0; i < points.length - 1; i++) {\n                    const diff = Math.abs(points[i].ts - target);\n                    if (diff < bestDiff) {\n                        best = points[i];\n                        bestDiff = diff;\n                    }\n                }\n                if (!best || bestDiff > toleranceSeconds * 1000) return null;\n                return latest.level - best.level;\n            }\n\n            const hour = deltaNear(3600, 45 * 60);\n            const day = deltaNear(24 * 3600, 3 * 3600);\n\n            let lastRiseTs = null;\n            for (let i = points.length - 1; i >= 1; i--) {\n                if (points[i].level > points[i-1].level) {\n                    lastRiseTs = points[i].ts;\n                    break;\n                }\n            }\n            \/* \u201eRast\u201d koristimo samo dok je zadnji potvr\u0111eni pozitivni pomak mla\u0111i od 60 min.\n               Nakon toga prikaz prelazi na neutralniji naziv \u201eTrend\u201d. *\/\n            const hasRecentRise = lastRiseTs !== null && (Date.now() - lastRiseTs) <= 3600 * 1000;\n\n            return {prefix: hasRecentRise ? 'Rast' : 'Trend', minute, hour, day};\n        }\n\n        function formatDubrovacakRate(value, decimals) {\n            const n = toNum(value);\n            if (!Number.isFinite(n)) return '\u2014';\n            const sign = n > 0 ? '+' : '';\n            return sign + fmt(n, decimals) + ' cm';\n        }\n\n        function renderDubrovacakRates(station) {\n            const minuteLabel = qs('dub-rate-minute-label');\n            const hourLabel = qs('dub-rate-hour-label');\n            const dayLabel = qs('dub-rate-day-label');\n            const minuteEl = qs('dub-rate-minute');\n            const hourEl = qs('dub-rate-hour');\n            const dayEl = qs('dub-rate-day');\n            const prepEl = qs('dub-rate-preparation');\n\n            \/* Ovdje vi\u0161e ne prikazujemo izvedenu \"brzinu po minuti\" ni promjenu u 1 h.\n               Za stanovnika su stabilnije i razumljivije promjene 24 h \/ 3 dana \/ 7 dana. *\/\n            const ch24 = station && station.ok ? waterRangeChange(station, '24h') : null;\n            const ch3  = station && station.ok ? waterRangeChange(station, '3d') : null;\n            const ch7  = station && station.ok ? waterRangeChange(station, '7d') : null;\n\n            if (hourLabel) hourLabel.textContent = 'Promjena u 24 h';\n            if (dayLabel) dayLabel.textContent = 'Promjena u 3 dana';\n            if (minuteLabel) minuteLabel.textContent = 'Promjena u 7 dana';\n            if (hourEl) hourEl.textContent = formatDubrovacakRate(ch24, 0);\n            if (dayEl) dayEl.textContent = formatDubrovacakRate(ch3, 0);\n            if (minuteEl) minuteEl.textContent = formatDubrovacakRate(ch7, 0);\n\n            [[hourEl, ch24], [dayEl, ch3], [minuteEl, ch7]].forEach(([el, v]) => {\n                if (!el) return;\n                const d = waterDirection(v);\n                el.classList.toggle('is-up', d === 'up');\n                el.classList.toggle('is-down', d === 'down');\n            });\n            if (prepEl) {\n                const level = Number(station?.level_cm);\n                const prep = Number(station?.limits?.preparation);\n                if (Number.isFinite(level) && Number.isFinite(prep)) {\n                    const gap = prep - level;\n                    prepEl.textContent = gap > 0 ? fmt(gap,0) + ' cm' : (gap === 0 ? '0 cm' : 'Prag prije\u0111en');\n                } else {\n                    prepEl.textContent = '\u2014';\n                }\n            }\n        }\n\n        function dubrovacakDailyExtremes(station) {\n            const rows = (Array.isArray(station?.history_30d) ? station.history_30d : [])\n                .filter(r => r && Number.isFinite(Number(r.level_cm)))\n                .map(r => ({\n                    level:Number(r.level_cm),\n                    ts:Number(r.timestamp || 0),\n                    date:String(r.date || '')\n                }))\n                .sort((a,b) => (a.ts || 0) - (b.ts || 0));\n\n            if (rows.length < 2) return {rise:null, fall:null, min:null, max:null, days:rows.length};\n            const deltas = [];\n            for (let i=1; i<rows.length; i++) deltas.push(rows[i].level - rows[i-1].level);\n            const rises = deltas.filter(v => v > 0);\n            const falls = deltas.filter(v => v < 0);\n            return {\n                rise: rises.length ? Math.max.apply(null, rises) : 0,\n                fall: falls.length ? Math.min.apply(null, falls) : 0,\n                min: Math.min.apply(null, rows.map(r => r.level)),\n                max: Math.max.apply(null, rows.map(r => r.level)),\n                days: rows.length\n            };\n        }\n\n        function dubrovacakTrendStatusHtml(station) {\n            if (!station || !station.ok) {\n                return '<div class=\"mv-dub-chart-empty\">Tendencija i sigurnosni status trenuta\u010dno nisu dostupni.<\/div>';\n            }\n\n            const level = toNum(station.level_cm);\n            const ch24 = waterRangeChange(station, '24h');\n            const dir = waterDirection(ch24);\n            const directionLabel = dir === 'up' ? 'RASTE' : dir === 'down' ? 'PADA' : (Number.isFinite(toNum(ch24)) ? 'STABILNO' : 'NEMA DOVOLJNO PODATAKA');\n            const directionClass = dir === 'up' ? 'is-up' : dir === 'down' ? 'is-down' : 'is-flat';\n            const prep = toNum(station?.limits?.preparation);\n            const gap = Number.isFinite(level) && Number.isFinite(prep) ? prep - level : NaN;\n            const gapText = Number.isFinite(gap) ? (gap > 0 ? fmt(gap,0) + ' cm' : gap === 0 ? '0 cm' : fmt(Math.abs(gap),0) + ' cm iznad') : '\u2014';\n            const statusLabel = String(station.label || 'INFORMATIVNO').replace('BEZ AKTIVNIH MJERA', 'BEZ AKTIVNIH MJERA OBRANE');\n            const ext = dubrovacakDailyExtremes(station);\n            const rise = Number.isFinite(ext.rise) ? (ext.rise > 0 ? '+' : '') + fmt(ext.rise,0) + ' cm' : '\u2014';\n            const fall = Number.isFinite(ext.fall) ? (ext.fall > 0 ? '+' : '') + fmt(ext.fall,0) + ' cm' : '\u2014';\n            const range = Number.isFinite(ext.min) && Number.isFinite(ext.max) ? fmt(ext.min,0) + '\u2013' + fmt(ext.max,0) + ' cm' : '\u2014';\n            const change24 = Number.isFinite(toNum(ch24)) ? formatDubrovacakRate(ch24, 0) : '\u2014';\n            const narrative = Number.isFinite(toNum(ch24))\n                ? (dir === 'up' ? 'Vodostaj je u posljednja 24 sata vi\u0161i za ' + fmt(Math.abs(ch24),0) + ' cm.'\n                    : dir === 'down' ? 'Vodostaj je u posljednja 24 sata ni\u017ei za ' + fmt(Math.abs(ch24),0) + ' cm.'\n                    : 'Vodostaj je u posljednja 24 sata bez zna\u010dajne promjene.')\n                : 'Za pouzdanu 24-satnu usporedbu jo\u0161 nema dovoljno slu\u017ebenih mjerenja.';\n\n            return '<div class=\"mv-dub-status-head\">' +\n                    '<div><div class=\"mv-dub-chart-title\">Tendencija i sigurnosni status<\/div>' +\n                    '<div class=\"mv-dub-detail-subtitle\">Sa\u017eetak stvarnih slu\u017ebenih mjerenja \u00b7 nije prognoza<\/div><\/div>' +\n                    '<div class=\"mv-dub-status-source\">Dubrov\u010dak \u00b7 Sava<\/div>' +\n                '<\/div>' +\n                '<div class=\"mv-dub-status-lead\">' +\n                    '<div class=\"mv-dub-status-direction\">' +\n                        '<span>Smjer \u00b7 24 h<\/span>' +\n                        '<strong class=\"'+directionClass+'\">'+escapeHtml(directionLabel)+'<\/strong>' +\n                        '<b class=\"'+directionClass+'\">'+escapeHtml(change24)+'<\/b>' +\n                        '<p>'+escapeHtml(narrative)+'<\/p>' +\n                    '<\/div>' +\n                    '<div class=\"mv-dub-status-safety\">' +\n                        '<span>Sigurnosni status<\/span>' +\n                        '<strong>'+escapeHtml(statusLabel)+'<\/strong>' +\n                        '<div><span>Do pripremnog stanja<\/span><b>'+escapeHtml(gapText)+'<\/b><\/div>' +\n                        '<small>Pripremno '+(Number.isFinite(prep) ? escapeHtml(fmt(prep,0))+' cm' : '\u2014')+'<\/small>' +\n                    '<\/div>' +\n                '<\/div>' +\n                '<div class=\"mv-dub-status-stats\">' +\n                    '<div><span>Najve\u0107i dnevni porast \u00b7 30 dana<\/span><strong class=\"is-up\">'+escapeHtml(rise)+'<\/strong><\/div>' +\n                    '<div><span>Najve\u0107i dnevni pad \u00b7 30 dana<\/span><strong class=\"is-down\">'+escapeHtml(fall)+'<\/strong><\/div>' +\n                    '<div><span>Raspon vodostaja \u00b7 30 dana<\/span><strong>'+escapeHtml(range)+'<\/strong><\/div>' +\n                '<\/div>';\n        }\n\n        \/* Za du\u017ee raspone stupci po svakom mjerenju postaju pretanki i ne\u010ditljivi (stotine\n           stupaca). Kao kod hidrolo\u0161kih agencija, promjena se tada zbraja po intervalu:\n           3 dana \u2192 po 3 sata, 7 dana \u2192 po 6 sati, 14\/30 dana \u2192 po danu. *\/\n        const DUB_BAR_BUCKET_HOURS = {'24h':0, '3d':3, '7d':6, '14d':24, '30d':24};\n\n        function dubrovacakBucketRows(rows, bucketHours) {\n            const clean = (Array.isArray(rows) ? rows : [])\n                .filter(r => r && Number.isFinite(Number(r.level_cm)) && Number(r.timestamp||0) > 0)\n                .sort((a,b) => Number(a.timestamp) - Number(b.timestamp));\n            if (!bucketHours) return clean;\n            const size = bucketHours * 3600;\n            const byBucket = new Map();\n            clean.forEach(r => {\n                const d = new Date(Number(r.timestamp)*1000);\n                \/* granice intervala po lokalnom vremenu (npr. 00\u201306, 06\u201312 ...) *\/\n                const localMidnight = new Date(d.getFullYear(), d.getMonth(), d.getDate()).getTime()\/1000;\n                const key = localMidnight + Math.floor((Number(r.timestamp) - localMidnight) \/ size) * size;\n                byBucket.set(key, r); \/* zadnje mjerenje u intervalu *\/\n            });\n            return Array.from(byBucket.values());\n        }\n\n        function renderDubrovacakDetail(data) {\n            const station = data?.water?.sava?.dubrovacak || null;\n            const levelEl = qs('dub-detail-level');\n            const trendEl = qs('dub-detail-trend');\n            const airEl = qs('dub-detail-air');\n            const timeEl = qs('dub-detail-time');\n            const statusEl = qs('dub-detail-status');\n            const crossEl = qs('dub-cross-section');\n            const summary24 = qs('dub-24h-summary');\n            const graphMain = qs('dub-chart-main');\n            const trendPanel = qs('dub-trend-status');\n\n            if (!levelEl) return;\n            if (!station || !station.ok) {\n                levelEl.textContent = '\u2014';\n                if (trendEl) trendEl.textContent = '\u2014';\n                if (airEl) airEl.textContent = '\u2014';\n                if (timeEl) timeEl.textContent = 'Podatak nije dostupan';\n                if (statusEl) statusEl.innerHTML = makeWaterStatus('NEDOSTUPNO', 'warn');\n                const arrowX = qs('dub-detail-arrow'); if (arrowX) { arrowX.className = 'mv-dubx-arrow'; arrowX.innerHTML = ''; }\n                const gaugeX = qs('dub-detail-gauge'); if (gaugeX) gaugeX.innerHTML = '';\n                renderDubrovacakRates(null);\n                if (summary24) summary24.innerHTML = '';\n                if (graphMain) graphMain.innerHTML = '';\n                if (trendPanel) trendPanel.innerHTML = '';\n                if (crossEl) crossEl.innerHTML = '<div class=\"mv-dub-chart-empty\">Slu\u017ebeni vodostaj trenuta\u010dno nije dostupan.<\/div>';\n                return;\n            }\n\n            levelEl.innerHTML = escapeHtml(fmt(station.level_cm,0)) + '<small>cm<\/small>';\n            const arrowD = qs('dub-detail-arrow');\n            const trD = toNum(station.trend);\n            if (arrowD) {\n                const dirD = waterDirection(trD);\n                arrowD.className = 'mv-dubx-arrow' + (dirD ? ' is-visible is-' + dirD : '');\n                arrowD.innerHTML = dirD ? waterArrowSvg(trD) : '';\n            }\n            const gaugeD = qs('dub-detail-gauge');\n            if (gaugeD) gaugeD.innerHTML = waterGaugeHtml(station);\n            if (statusEl) {\n                let mode = '';\n                if (['regular','preparation'].includes(station.status)) mode = 'warn';\n                if (['extraordinary','emergency'].includes(station.status)) mode = 'danger';\n                statusEl.innerHTML = makeWaterStatus(station.label || 'INFORMATIVNO', mode);\n            }\n            const tr = Number(station.trend);\n            if (trendEl) {\n                trendEl.textContent = Number.isFinite(tr) ? signedCm(tr) : '\u2014';\n                trendEl.className = waterDirection(tr) === 'up' ? 'is-up' : waterDirection(tr) === 'down' ? 'is-down' : '';\n            }\n\n            const air = dubrovacakAirTemperature(data);\n            if (airEl) airEl.textContent = Number.isFinite(air) ? fmt(air,1) + ' \u00b0C' : '\u2014';\n\n            const official = station.display_time || formatStamp(station.measured_at);\n            const checked = formatClock(data?.generated_at || new Date());\n            if (timeEl) timeEl.innerHTML = escapeHtml(official) + '<br><span style=\"font-size:11px;color:#8293a3;font-weight:500\">provjereno '+escapeHtml(checked)+'<\/span>';\n\n            renderDubrovacakRates(station);\n            if (crossEl) crossEl.innerHTML = dubrovacakCrossSectionHtml(station);\n\n            \/* Jedan graf + jedan raspon (24 sata\/3\/7\/14\/30 dana), isti kontrolni mehanizam kao\n               glavna kartica Save (waterGraphForRange) \u2013 umjesto tri odvojena, djelomi\u010dno\n               preklopljena grafa (24h\/48h\/30d) koja su prije stajala jedan ispod drugog. *\/\n            const cfg = WATER_RANGES[dubRange] || WATER_RANGES['24h'];\n            if (summary24) summary24.innerHTML = dubrovacak24hSummaryHtml(station, dubRange);\n\n            let graph = waterGraphForRange(station, dubRange);\n            if (dubRange === '24h') {\n                \/* Isti niz mjerenja kao sa\u017eetak iznad (gusta povijest), da se brojke poklapaju. *\/\n                const dense = dubrovacakHistoryRows(station);\n                if (dense.length >= 2) {\n                    const cut = dense[dense.length - 1].timestamp - 24*3600;\n                    graph = {mode:'hourly', rows: dense.filter(r => r.timestamp >= cut)};\n                }\n            }\n            const bandMode = graph.mode === 'band';\n            if (graphMain) graphMain.innerHTML = detailedWaterChartHtml(graph.rows, {\n                title: 'Vodostaj \u00b7 ' + cfg.shortLabel,\n                subtitle: bandMode ? 'Dnevni raspon (sjena) i zadnje mjerenje dana (linija)' : 'Stvarni slu\u017ebeni vodostaj kroz vrijeme',\n                mode: bandMode ? 'day' : (dubRange === '24h' ? 'time' : 'week'),\n                band: bandMode,\n                showEndpoints: !bandMode,\n                limits: station.limits\n            });\n            if (trendPanel) trendPanel.innerHTML = dubrovacakTrendStatusHtml(station);\n\n            root.querySelectorAll('[data-dub-range-btn]').forEach(btn => {\n                const active = btn.getAttribute('data-dub-range-btn') === dubRange;\n                btn.classList.toggle('is-active', active);\n                btn.setAttribute('aria-pressed', active ? 'true' : 'false');\n            });\n        }\n\n        \/* Rang rasta: tri postaje s najve\u0107im pozitivnim porastom od zadnjeg mjerenja.\n           1. mjesto je dinami\u010dno: naran\u010dasta (blagi porast) \u2192 crvena (jak porast).\n           Skala (promjena u 24 h): RISE_MILD_CM = po\u010detak (naran\u010dasta), RISE_STRONG_CM = puna crvena. *\/\n        const RISE_MILD_CM = 2;\n        const RISE_STRONG_CM = 60;\n        const RISE_VARS = ['--mv-rise-bg-1','--mv-rise-bg-2','--mv-rise-border','--mv-rise-shadow','--mv-rise-accent'];\n\n        function riseIntensity(trend) {\n            return Math.max(0, Math.min(1, (trend - RISE_MILD_CM) \/ (RISE_STRONG_CM - RISE_MILD_CM)));\n        }\n\n        function applySavaRiseRanking(sava) {\n            const rankLabels = ['Najbr\u017ei rast \u00b7 24 h', '2. rast \u00b7 24 h', '3. rast \u00b7 24 h'];\n            SAVA_ORDER.forEach(key => {\n                const box = qs('water-' + key);\n                if (box) {\n                    box.classList.remove('is-rise-1','is-rise-2','is-rise-3');\n                    RISE_VARS.forEach(v => box.style.removeProperty(v));\n                }\n                const rank = qs('water-' + key + '-rank');\n                if (rank) { rank.classList.remove('is-visible'); rank.textContent = ''; }\n            });\n\n            const ranked = SAVA_ORDER.map((key, order) => {\n                const station = sava && sava[key] ? sava[key] : null;\n                \/* Rang po promjeni u zadnja 24 h (stabilnije od jednog mjerenja, koje mo\u017ee\n                   biti \u0161um i proturje\u010diti grafu). *\/\n                const trend = station && station.ok ? toNum(waterRangeChange(station, '24h')) : NaN;\n                return {key, order, trend};\n            }).filter(item => Number.isFinite(item.trend) && item.trend > 0)\n              .sort((a, b) => (b.trend - a.trend) || (a.order - b.order));\n\n            const wrap = root.querySelector('.mv-water-sava');\n            if (wrap) wrap.classList.toggle('has-rank', ranked.length > 0);\n\n            ranked.slice(0, 3).forEach((item, index) => {\n                const box = qs('water-' + item.key);\n                if (box) {\n                    box.classList.add('is-rise-' + (index + 1));\n                    if (index === 0) {\n                        const t = riseIntensity(item.trend);\n                        const hue = Math.round(28 - 28 * t);            \/* 28\u00b0 naran\u010dasta \u2192 0\u00b0 crvena *\/\n                        box.style.setProperty('--mv-rise-bg-1', 'hsl(' + hue + ',100%,' + Math.round(97 - 2 * t) + '%)');\n                        box.style.setProperty('--mv-rise-bg-2', 'hsl(' + hue + ',100%,' + Math.round(93 - 4 * t) + '%)');\n                        box.style.setProperty('--mv-rise-border', 'hsl(' + hue + ',' + Math.round(78 + 6 * t) + '%,' + Math.round(72 - 8 * t) + '%)');\n                        box.style.setProperty('--mv-rise-shadow', 'hsla(' + hue + ',88%,52%,' + (0.10 + 0.10 * t).toFixed(2) + ')');\n                        box.style.setProperty('--mv-rise-accent', 'hsl(' + hue + ',' + Math.round(84 + 4 * t) + '%,' + Math.round(50 - 6 * t) + '%)');\n                    }\n                }\n                const rank = qs('water-' + item.key + '-rank');\n                if (rank) {\n                    const strong = index === 0 && riseIntensity(item.trend) >= 0.66;\n                    rank.textContent = strong ? 'Jak porast \u00b7 24 h' : rankLabels[index];\n                    rank.classList.add('is-visible');\n                }\n            });\n        }\n\n        \/* Retci promjene su ujedno kontrola grafa kartice (nema zasebnog izbornika raspona). *\/\n        const WATER_CARD_PERIODS = [\n            {key:'3d',  label:'3 dana'},\n            {key:'7d',  label:'7 dana'},\n            {key:'30d', label:'30 dana'}\n        ];\n\n        function waterChangeValueHtml(v, compact) {\n            const n = toNum(v);\n            if (!Number.isFinite(n)) return '<strong class=\"is-none\">\u2014<\/strong>';\n            const dir = waterDirection(n);\n            const cls = dir === 'up' ? 'is-up' : dir === 'down' ? 'is-down' : 'is-flat';\n            const txt = compact ? signedCm(n).replace(' cm', '') + '<small>cm<\/small>' : escapeHtml(signedCm(n));\n            return '<strong class=\"' + cls + '\">' + waterArrowSvg(n) + '<b>' + txt + '<\/b><\/strong>';\n        }\n\n        \/* Svako razdoblje u svom punom retku (24 h, 3, 7, 30 dana) \u2013 \u010ditljivije od stupaca.\n           Redak je ujedno kontrola grafa kartice. *\/\n        function waterChangesHtml(station, range) {\n            return ['24h','3d','7d','30d'].map(key =>\n                '<button type=\"button\" class=\"mv-wc-main' + (range === key ? ' is-selected' : '') + '\" data-card-range=\"' + key + '\" aria-pressed=\"' + (range === key) + '\">' +\n                    '<span>' + escapeHtml(WATER_RANGES[key].trendLabel) + '<\/span>' + waterChangeValueHtml(waterRangeChange(station, key)) +\n                '<\/button>').join('');\n        }\n\n        function waterStationByKey(key) {\n            const w = snapshotData && snapshotData.water ? snapshotData.water : {};\n            if (key === 'odra' || key === 'kupa') return w.odra_kupa ? w.odra_kupa[key] : null;\n            return (w.sava && w.sava[key]) || w[key] || null;\n        }\n\n        function renderWater(stationKey, station, range) {\n            const box = qs('water-' + stationKey);\n            if (!box) return;\n            range = range || box.dataset.range || '24h';\n            box.dataset.range = range;\n            const lastEl = qs('water-' + stationKey + '-last');\n            const statusEl  = qs('water-' + stationKey + '-status');\n            const changesEl = qs('water-' + stationKey + '-trend');\n            const freshEl   = qs('water-' + stationKey + '-time');\n            const extraEl   = qs('water-' + stationKey + '-extra');\n            const gaugeEl   = qs('water-' + stationKey + '-gauge');\n            const levelEl   = box.querySelector('.mv-water-level');\n\n            const arrowEl = qs('water-' + stationKey + '-arrow');\n            if (!station || !station.ok) {\n                if (arrowEl) { arrowEl.className = 'mv-water-arrow'; arrowEl.innerHTML = ''; }\n                if (lastEl) lastEl.innerHTML = '';\n                levelEl.innerHTML = '<span class=\"mv-water-level-unavailable\">Podatak nije dostupan<\/span>';\n                box.classList.add('is-unavailable');\n                if (statusEl) statusEl.innerHTML = makeWaterStatus('NEDOSTUPNO', 'warn');\n                if (changesEl) changesEl.innerHTML = '';\n                if (gaugeEl) gaugeEl.innerHTML = '';\n                if (freshEl) { freshEl.className = 'mv-water-fresh'; freshEl.title = ''; freshEl.textContent = 'Izvor trenuta\u010dno nije vratio valjano mjerenje.'; }\n                if (extraEl) extraEl.textContent = '';\n                renderWaterHistory(stationKey, station, range);\n                return;\n            }\n\n            const levelTxt = fmt(station.level_cm, 0);\n            levelEl.dataset.chars = String(levelTxt).length;\n            levelEl.innerHTML = '<span class=\"mv-water-level-value\">' + escapeHtml(levelTxt) + '<\/span><span class=\"mv-water-level-unit\">cm<\/span>';\n            box.classList.remove('is-unavailable');\n\n            const trend = toNum(station.trend);\n            if (arrowEl) {\n                const dir = waterDirection(trend);\n                arrowEl.className = 'mv-water-arrow' + (dir ? ' is-visible is-' + dir : '');\n                arrowEl.innerHTML = dir ? waterArrowSvg(trend) : '';\n                arrowEl.title = dir ? 'Od zadnjeg mjerenja: ' + signedCm(trend) : '';\n            }\n            if (lastEl) {\n                lastEl.innerHTML = '<span>Od zadnjeg mjerenja<\/span>' + waterChangeValueHtml(trend);\n            }\n\n            if (freshEl) {\n                const fresh = waterFreshness(station);\n                freshEl.className = 'mv-water-fresh ' + fresh.cls;\n                freshEl.title = station.display_time ? 'Slu\u017ebeno mjerenje: ' + station.display_time : '';\n                freshEl.innerHTML = '<span class=\"mv-fresh-dot\"><\/span><span>' + fresh.html + '<\/span>';\n            }\n\n            if (changesEl) changesEl.innerHTML = waterChangesHtml(station, range);\n\n            if (gaugeEl) gaugeEl.innerHTML = waterGaugeHtml(station);\n\n            let mode = '';\n            if (['no_measures','information'].includes(station.status)) mode = 'neutral';\n            if (['regular','preparation'].includes(station.status)) mode = 'warn';\n            if (['extraordinary','emergency'].includes(station.status)) mode = 'danger';\n            if (statusEl) {\n                \/* \"Informativno\" (npr. ARSO automatska postaja) je podatak o izvoru, ne stanje \u2013\n                   prikazuje se kao obi\u010dan tekst, a ne kao oznaka stanja. *\/\n                statusEl.innerHTML = station.status === 'information'\n                    ? '<span class=\"mv-water-info\">' + escapeHtml(station.label || 'Informativno mjerenje') + '<\/span>'\n                    : makeWaterStatus(station.label || 'INFORMATIVNO', mode);\n            }\n\n            if (extraEl) {\n                const extras = [];\n                if (station.secondary && station.secondary.ok) {\n                    let secondaryLine = 'DHMZ: ' + fmt(station.secondary.level_cm, 0) + ' cm';\n                    if (station.secondary.display_time) secondaryLine += ' \u00b7 ' + station.secondary.display_time;\n                    extras.push(secondaryLine);\n                }\n                if (Number.isFinite(Number(station.flow_m3s))) extras.push('Protok ' + fmt(station.flow_m3s, 1) + ' m\u00b3\/s');\n                if (Number.isFinite(Number(station.water_temp))) extras.push('Voda ' + fmt(station.water_temp, 1) + ' \u00b0C');\n                extraEl.textContent = extras.join(' \u00b7 ');\n            }\n\n            renderWaterHistory(stationKey, station, range);\n        }\n\n        function renderWarnings(payload) {\n            const title = qs('warning-title');\n            const textEl = qs('warning-text');\n            const list = qs('warning-list');\n            const icon = qs('warning-icon');\n            const time = qs('warning-time');\n            const advice = qs('warning-advice');\n            const adviceText = qs('warning-advice-text');\n            if (!title || !list) return;\n\n            list.innerHTML = '';\n            if (advice) advice.hidden = true;\n            if (adviceText) adviceText.textContent = '';\n            if (time) time.textContent = 'Provjera: ' + formatStamp(payload?.checked_at);\n\n            const iconCheck = '<svg viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2.3\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><path d=\"M20 6 9 17l-5-5\"><\/path><\/svg>';\n            const iconAlert = '<svg viewBox=\"0 0 64 56\"><path d=\"M32 3 L61 53 H3 Z\" fill=\"currentColor\" stroke=\"rgba(15,23,42,.18)\" stroke-width=\"2\"><\/path><rect x=\"29.5\" y=\"17\" width=\"5\" height=\"20\" rx=\"2.5\" fill=\"var(--mv-warning-mark)\"><\/rect><circle cx=\"32\" cy=\"44\" r=\"3\" fill=\"var(--mv-warning-mark)\"><\/circle><\/svg>';\n\n            if (!payload || payload.ok !== true) {\n                title.textContent = 'PROVJERA NIJE DOSTUPNA';\n                title.style.color = '#9a6500';\n                if (textEl) textEl.textContent = payload?.message || 'DHMZ CAP trenuta\u010dno nije mogu\u0107e provjeriti.';\n                if (icon) { icon.innerHTML = iconAlert; icon.className = 'mv-warning-symbol is-unavailable'; }\n                return;\n            }\n\n            const warnings = Array.isArray(payload.warnings) ? payload.warnings : [];\n            if (!warnings.length) {\n                title.textContent = 'NEMA IZDANIH UPOZORENJA';\n                title.style.color = '#2eab60';\n                if (textEl) textEl.textContent = 'DHMZ CAP trenuta\u010dno ne sadr\u017ei \u017euto, naran\u010dasto ni crveno upozorenje.';\n                if (icon) { icon.innerHTML = iconCheck; icon.className = 'mv-warning-symbol is-clear'; }\n                return;\n            }\n\n            const top = warnings[0];\n            title.textContent = top.level_label + ' UPOZORENJE';\n            title.style.color = top.level === 'red' ? '#b71921' : top.level === 'orange' ? '#c65f00' : '#9a7900';\n            if (textEl) textEl.textContent = 'Slu\u017ebeno DHMZ upozorenje za ' + (payload.region || 'Zagreba\u010dku regiju') + '.';\n            if (icon) {\n                icon.innerHTML = iconAlert;\n                const severityClass = top.level === 'red' ? 'is-red' : top.level === 'orange' ? 'is-orange' : 'is-yellow';\n                icon.className = 'mv-warning-symbol ' + severityClass;\n            }\n\n            warnings.forEach(w => {\n                const item = document.createElement('div');\n                item.className = 'mv-warning-item ' + (w.level || 'yellow');\n                const from = w.onset?.display || '';\n                const to = w.expires?.display || '';\n                const period = from || to ? ('Vrijedi: ' + (from || '\u2014') + (to ? ' \u2013 ' + to : '')) : '';\n                const desc = w.headline || w.description || '';\n                item.innerHTML =\n                    '<div class=\"mv-warning-head\"><div><div class=\"mv-warning-level\">' + (w.level_label || '') + '<\/div>' +\n                    '<div class=\"mv-warning-event\">' + escapeHtml(w.event || w.headline || 'DHMZ upozorenje') + '<\/div><\/div><\/div>' +\n                    (period ? '<div class=\"mv-warning-time\">' + escapeHtml(period) + '<\/div>' : '') +\n                    (desc ? '<div class=\"mv-warning-desc\">' + escapeHtml(desc) + '<\/div>' : '');\n                list.appendChild(item);\n            });\n\n            const warningWithAdvice = warnings.find(w =>\n                String(w.instruction || '').trim() !== ''\n            );\n\n            if (warningWithAdvice && advice && adviceText) {\n                adviceText.textContent = String(warningWithAdvice.instruction).trim();\n                advice.hidden = false;\n            }\n        }\n\n\n        let dhmzRadarTimer = null;\n        let dhmzRadarFrames = [];\n        let dhmzRadarIndex = 0;\n        let dhmzRadarPlaying = false;\n\n        function stopDhmzRadarAnimation() {\n            if (dhmzRadarTimer) clearInterval(dhmzRadarTimer);\n            dhmzRadarTimer = null;\n            dhmzRadarPlaying = false;\n            const btn = qs('dhmz-radar-play');\n            if (btn && dhmzRadarFrames.length > 1) btn.textContent = '\u25b6 Animacija';\n        }\n\n        \/* Svi kadrovi se u\u010ditavaju jednom (jedan cache-bust po osvje\u017eavanju podataka) i\n           sla\u017eu jedan na drugi; animacija samo pretapa prozirnost. Ranije se svaki kadar\n           iznova preuzimao pri svakom prikazu (?_mv=Date.now()), pa je slika treperila i trzala. *\/\n        let dhmzRadarLayers = [];\n\n        function showDhmzRadarFrame(index) {\n            const badge = qs('dhmz-radar-badge');\n            if (!dhmzRadarLayers.length) return;\n            dhmzRadarIndex = ((index % dhmzRadarLayers.length) + dhmzRadarLayers.length) % dhmzRadarLayers.length;\n            dhmzRadarLayers.forEach((img, i) => img.classList.toggle('is-on', i === dhmzRadarIndex));\n            if (badge) badge.textContent = 'DHMZ \u00b7 ' + (dhmzRadarLayers.length > 1 ? (dhmzRadarIndex + 1) + '\/' + dhmzRadarLayers.length : 'aktualno');\n        }\n\n        function buildDhmzRadarLayers(frames, stamp, onReady) {\n            const baseImg = qs('dhmz-radar-img');\n            const frame = baseImg ? baseImg.parentElement : null;\n            if (!frame) return;\n            frame.querySelectorAll('.mv-dhmz-radar-layer').forEach(el => el.remove());\n            if (baseImg) baseImg.style.display = 'none';\n            let loaded = 0, done = false;\n            const finish = () => { if (!done) { done = true; onReady(); } };\n            dhmzRadarLayers = frames.map((url, i) => {\n                const img = new Image();\n                img.className = 'mv-dhmz-radar-layer';\n                img.alt = i === frames.length - 1 ? 'DHMZ radarska slika \u2013 kompozit' : '';\n                img.decoding = 'async';\n                img.onload = img.onerror = function () {\n                    if (i === frames.length - 1 && img.naturalWidth && img.naturalHeight) {\n                        frame.style.aspectRatio = img.naturalWidth + ' \/ ' + img.naturalHeight;\n                    }\n                    loaded++;\n                    if (loaded >= frames.length) finish();\n                };\n                img.src = url + (url.includes('?') ? '&' : '?') + '_mv=' + encodeURIComponent(stamp);\n                frame.insertBefore(img, frame.firstChild);\n                return img;\n            });\n            setTimeout(finish, 8000); \/* animacija krene i ako neki kadar kasni *\/\n        }\n\n        function startDhmzRadarAnimation() {\n            if (dhmzRadarFrames.length < 2) return;\n            stopDhmzRadarAnimation();\n            dhmzRadarPlaying = true;\n            const btn = qs('dhmz-radar-play');\n            if (btn) btn.textContent = '\u275a\u275a Pauza';\n            dhmzRadarTimer = setInterval(function () {\n                showDhmzRadarFrame(dhmzRadarIndex + 1);\n            }, 700);\n        }\n\n        function renderDhmzRadar(payload) {\n            const img = qs('dhmz-radar-img');\n            const btn = qs('dhmz-radar-play');\n            const note = qs('dhmz-radar-note');\n            if (!img) return;\n\n            stopDhmzRadarAnimation();\n            const frames = Array.isArray(payload?.frames) ? payload.frames.filter(Boolean) : [];\n            dhmzRadarFrames = frames.length ? frames : ['https:\/\/vrijeme.hr\/kompozit-stat.png'];\n            dhmzRadarIndex = Math.max(0, dhmzRadarFrames.length - 1);\n            const stamp = String(snapshotData?.generated_at || Date.now());\n            const autoPlay = !(window.matchMedia && window.matchMedia('(prefers-reduced-motion: reduce)').matches);\n            buildDhmzRadarLayers(dhmzRadarFrames, stamp, function () {\n                showDhmzRadarFrame(dhmzRadarIndex);\n                if (dhmzRadarFrames.length > 1 && autoPlay) startDhmzRadarAnimation();\n            });\n            showDhmzRadarFrame(dhmzRadarIndex);\n\n            if (btn) {\n                btn.disabled = dhmzRadarFrames.length < 2;\n                btn.textContent = dhmzRadarFrames.length > 1 ? '\u25b6 Animacija' : 'Aktualna slika';\n                if (!btn.dataset.bound) {\n                    btn.addEventListener('click', function () {\n                        if (dhmzRadarPlaying) stopDhmzRadarAnimation();\n                        else startDhmzRadarAnimation();\n                    });\n                    btn.dataset.bound = '1';\n                }\n            }\n\n            if (note) {\n                note.textContent = dhmzRadarFrames.length > 1\n                    ? 'Slu\u017ebeni DHMZ kompozit \u00b7 ' + dhmzRadarFrames.length + ' frameova \u00b7 radarska mjerenja svakih 5 min.'\n                    : 'Slu\u017ebena aktualna DHMZ radarska slika. Ako DHMZ trenuta\u010dno ne izla\u017ee frameove animacije, koristite \u201eOtvori na DHMZ\u201d.';\n            }\n\n        }\n\n        function renderNext3Hours(minutely) {\n            const holder = qs('nowcast-track');\n            if (!holder) return;\n\n            const times = Array.isArray(minutely?.time) ? minutely.time : [];\n            if (!times.length) {\n                holder.innerHTML = '<div class=\"mv-nowcast-empty\">15-minutna prognoza trenuta\u010dno nije dostupna.<\/div>';\n                return;\n            }\n\n            const nowMs = Date.now();\n            let start = times.findIndex(t => {\n                const ms = new Date(t).getTime();\n                return Number.isFinite(ms) && ms >= nowMs - 5 * 60 * 1000;\n            });\n            if (start < 0) start = 0;\n\n            const end = Math.min(times.length, start + 13); \/\/ sada + pribli\u017eno 3 sata\n            let html = '';\n            for (let i = start; i < end; i++) {\n                const dt = new Date(times[i]);\n                const timeLabel = Number.isFinite(dt.getTime())\n                    ? dt.toLocaleTimeString('hr-HR', {hour:'2-digit', minute:'2-digit'})\n                    : '\u2014';\n                const temp = Number(minutely.temperature_2m?.[i]);\n                const rain = Number(minutely.precipitation?.[i]);\n                const speed = Number(minutely.wind_speed_10m?.[i]);\n                const gust = Number(minutely.wind_gusts_10m?.[i]);\n                const dir = Number(minutely.wind_direction_10m?.[i]);\n                const code = minutely.weather_code?.[i];\n                const dirLabel = Number.isFinite(dir) ? windDirection(dir) + ' ' : '';\n\n                html += '<div class=\"mv-nowcast-item' + (i === start ? ' is-first' : '') + '\">' +\n                    '<div class=\"mv-nowcast-time\">' + escapeHtml(timeLabel) + '<\/div>' +\n                    '<div class=\"mv-nowcast-icon\" title=\"' + escapeHtml(weatherDescription(code)) + '\">' + weatherIcon(code, minutely.is_day?.[i]) + '<\/div>' +\n                    '<strong class=\"mv-nowcast-temp\">' + fmt(temp, 1) + '\u00b0<\/strong>' +\n                    '<div class=\"mv-nowcast-rain\">\ud83d\udca7 ' + fmt(rain, 1) + ' mm<\/div>' +\n                    '<div class=\"mv-nowcast-wind\">' + escapeHtml(dirLabel) + fmt(speed, 0) + ' \/ ' + fmt(gust, 0) + ' km\/h<\/div>' +\n                '<\/div>';\n            }\n            holder.innerHTML = html || '<div class=\"mv-nowcast-empty\">Kratkoro\u010dna prognoza trenuta\u010dno nije dostupna.<\/div>';\n        }\n\n        function renderDays(daily) {\n            const holder = qs('days');\n            if (!holder) return;\n            holder.innerHTML = '';\n\n            const times = Array.isArray(daily.time) ? daily.time.slice(0, 7) : [];\n            times.forEach((t, i) => {\n                const div = document.createElement('div');\n                div.className = 'mv-day';\n\n                const code = daily.weather_code?.[i];\n                const rainAmount = daily.precipitation_sum?.[i];\n\n                div.innerHTML =\n                    '<div class=\"mv-day-top\">' + dayName(t) + '<\/div>' +\n                    '<div class=\"mv-day-date\">' + dateShort(t) + '<\/div>' +\n                    '<div class=\"mv-day-icon\">' + weatherIcon(code) + '<\/div>' +\n                    '<strong class=\"mv-max\">' + fmt(daily.temperature_2m_max?.[i], 0) + '\u00b0<\/strong>' +\n                    '<strong class=\"mv-min\">' + fmt(daily.temperature_2m_min?.[i], 0) + '\u00b0<\/strong>' +\n                    '<span class=\"mv-precip-small\">' + fmt(rainAmount, 1) + ' mm<\/span>';\n\n                holder.appendChild(div);\n            });\n        }\n\n        function renderAQI(aq) {\n            const info = aqiLabel(aq.european_aqi);\n            qs('aqi').textContent = fmt(aq.european_aqi, 0);\n            qs('face').innerHTML = info.face;\n\n            const pill = qs('aqi-pill');\n            pill.textContent = info.label;\n            pill.className = info.cls === 'danger' ? 'mv-pill danger' : info.cls === 'warn' ? 'mv-pill warn' : 'mv-pill';\n\n            const rowsEl = qs('aqi-rows');\n            if (rowsEl) rowsEl.innerHTML = AQI_POLLUTANTS.map(p => aqiRowHtml(p, aq ? aq[p.role] : null)).join('');\n        }\n\n        function renderUV(value) {\n            qs('uv').textContent = fmt(value, 0);\n            const info = uvLabel(value);\n            const pill = qs('uv-label');\n            pill.textContent = info.label;\n            pill.className = info.cls === 'danger' ? 'mv-pill danger' : info.cls === 'warn' ? 'mv-pill warn' : 'mv-pill neutral';\n\n            const colors = ['#34a853','#45b458','#63c356','#88cf4e','#c3d64c','#f0d34f','#f7b54b','#f79b43','#ef6e3f','#dd5040','#c43c43'];\n            const scale = qs('uv-scale');\n            const labels = qs('uv-labels');\n            scale.innerHTML = ''; labels.innerHTML = '';\n            colors.forEach((c, i) => {\n                const bar = document.createElement('div'); bar.className = 'mv-uv-bar'; bar.style.background = c; scale.appendChild(bar);\n                const lbl = document.createElement('div'); lbl.textContent = i + 1; labels.appendChild(lbl);\n            });\n            const last = document.createElement('div'); last.textContent = '11+'; labels.appendChild(last);\n            const lastBar = document.createElement('div'); lastBar.className = 'mv-uv-bar'; lastBar.style.background = '#8f2f7a'; scale.appendChild(lastBar);\n        }\n\n        \/* Razredi dnevne koli\u010dine oborina prema ETCCDI\/CLIMDEX (WMO): ki\u0161ni dan >= 1 mm,\n           obilna ki\u0161a >= 10 mm, vrlo obilna ki\u0161a >= 20 mm. Vidi mvmeteo_rain_help_html(). *\/\n        function precipClass(mm) {\n            const v = Number(mm) || 0;\n            if (v >= 20) return {cls:'very-heavy', color:'#1f5c96'};\n            if (v >= 10) return {cls:'heavy', color:'#4f93d1'};\n            if (v >= 1)  return {cls:'wet', color:'#a8d0f0'};\n            return {cls:'dry', color:'#e2e8f0'};\n        }\n\n        let rainRange = '7d';\n        let rainResizeTimer = null;\n        window.addEventListener('resize', function () {\n            clearTimeout(rainResizeTimer);\n            rainResizeTimer = setTimeout(function () { if (snapshotData && rainRange !== '7d') renderRain(snapshotData); }, 200);\n        });\n        const RAIN_MONTHS_FULL = ['sije\u010danj','velja\u010da','o\u017eujak','travanj','svibanj','lipanj','srpanj','kolovoz','rujan','listopad','studeni','prosinac'];\n\n        function rainDailyRows(history) {\n            const times = history?.daily?.time || [];\n            const vals = history?.daily?.precipitation_sum || [];\n            return times.map((t, i) => ({date:t, mm:Number(vals[i]) || 0, ok:vals[i] !== null && vals[i] !== undefined}));\n        }\n\n        function rainLegendDailyHtml() {\n            return '<div class=\"mv-gauge-legend\" aria-label=\"Legenda razreda oborina\"><span class=\"mv-gauge-legend-title\">Razredi:<\/span>' +\n                '<span><span class=\"mv-swatch\" style=\"background:#e2e8f0\"><\/span>suho<\/span>' +\n                '<span><span class=\"mv-swatch\" style=\"background:#a8d0f0\"><\/span>ki\u0161ni dan<\/span>' +\n                '<span><span class=\"mv-swatch\" style=\"background:#4f93d1\"><\/span>obilna ki\u0161a<\/span>' +\n                '<span><span class=\"mv-swatch\" style=\"background:#1f5c96\"><\/span>vrlo obilna ki\u0161a<\/span><\/div>';\n        }\n\n        function rainLegendMonthlyHtml() {\n            return '<div class=\"mv-gauge-legend\" aria-label=\"Legenda mjese\u010dnih oborina\"><span class=\"mv-gauge-legend-title\">Legenda:<\/span>' +\n                '<span><span class=\"mv-swatch\" style=\"background:#4f93d1\"><\/span>mjese\u010dna oborina<\/span>' +\n                '<span><span class=\"mv-swatch\" style=\"background:#b7d3ee\"><\/span>teku\u0107i mjesec<\/span>' +\n                '<span><span class=\"mv-swatch\" style=\"background:#16385f;height:3px;margin-top:5px\"><\/span>prosjek (Sisak 1949.\u20132024.)<\/span><\/div>';\n        }\n\n        function rainKv(label, valueHtml, first) {\n            return '<div class=\"mv-kv\"' + (first ? ' style=\"border-bottom:0;padding-top:6px\"' : '') + '><span>' + escapeHtml(label) + '<\/span><strong>' + valueHtml + '<\/strong><\/div>';\n        }\n\n        function rainDaysWord(n) { return n === 1 ? ' dan' : ' dana'; }\n\n        function renderRain7(rows) {\n            const holder = qs('rain-chart');\n            holder.innerHTML = '';\n            const last = rows.slice(-7);\n            let max = 0; last.forEach(r => { max = Math.max(max, r.mm); });\n            let total = 0, wet = 0;\n            last.forEach(r => {\n                total += r.mm; if (r.mm >= 1) wet++;\n                const pc = precipClass(r.mm);\n                const col = document.createElement('div'); col.className = 'mv-bar-col';\n                const height = max > 0 ? Math.max(4, (r.mm \/ max) * 120) : 4;\n                col.innerHTML = '<div class=\"mv-bar-value\">' + fmt(r.mm, 1) + '<\/div><div class=\"mv-bar\" style=\"height:' + height + 'px;background:' + pc.color + '\"><\/div><div class=\"mv-bar-label\">' + dateShort(r.date) + '<\/div>';\n                holder.appendChild(col);\n            });\n            return rainKv('Ukupno', escapeHtml(fmt(total, 1)) + ' mm', true) +\n                   rainKv('Ki\u0161nih dana (\u22651 mm)', wet + rainDaysWord(wet) + ' od ' + last.length);\n        }\n\n        function rainSvgWidth(holder) {\n            const w = Math.round((holder && holder.clientWidth) || (holder && holder.parentElement && holder.parentElement.clientWidth) || 640);\n            return Math.max(280, Math.min(900, w));\n        }\n\n        function niceMax(v) {\n            if (!(v > 0)) return 10;\n            const steps = [5,10,20,25,40,50,60,80,100,120,150,200,250,300,400,500];\n            for (const st of steps) if (v <= st) return st;\n            return Math.ceil(v \/ 100) * 100;\n        }\n\n        function renderRain30(rows, monthly) {\n            const holder = qs('rain-svg');\n            const last = rows.slice(-30);\n            const W = rainSvgWidth(holder), H = 210, L = 34, R = 8, T = 22, B = 34;\n            const cw = (W - L - R) \/ Math.max(1, last.length);\n            const maxV = niceMax(Math.max(...last.map(r => r.mm), 0));\n            const y = v => T + (H - T - B) * (1 - v \/ maxV);\n            let grid = '';\n            [0, maxV \/ 2, maxV].forEach(g => {\n                grid += '<line x1=\"' + L + '\" x2=\"' + (W - R) + '\" y1=\"' + y(g).toFixed(1) + '\" y2=\"' + y(g).toFixed(1) + '\" stroke=\"#e8eef4\"><\/line>' +\n                        '<text x=\"' + (L - 6) + '\" y=\"' + (y(g) + 4).toFixed(1) + '\" text-anchor=\"end\" font-size=\"11\" fill=\"#6f8398\">' + fmt(g, 0) + '<\/text>';\n            });\n            let bars = '', labels = '';\n            let total = 0, wet = 0, maxDay = null;\n            last.forEach((r, i) => {\n                total += r.mm; if (r.mm >= 1) wet++;\n                if (!maxDay || r.mm > maxDay.mm) maxDay = r;\n                const x = L + i * cw + cw * 0.15, w = cw * 0.7;\n                const top = r.mm > 0 ? Math.min(y(r.mm), H - B - 2) : H - B - 2;\n                const pc = precipClass(r.mm);\n                bars += '<rect x=\"' + x.toFixed(1) + '\" y=\"' + top.toFixed(1) + '\" width=\"' + w.toFixed(1) + '\" height=\"' + (H - B - top).toFixed(1) + '\" fill=\"' + pc.color + '\"><title>' + escapeHtml(dateShort(r.date) + ': ' + fmt(r.mm, 1) + ' mm') + '<\/title><\/rect>';\n                const step = W < 480 ? 7 : 5;\n                if ((i % step === 0 && i <= last.length - 1 - Math.ceil(step \/ 2)) || i === last.length - 1) {\n                    labels += '<text x=\"' + (x + w \/ 2).toFixed(1) + '\" y=\"' + (H - B + 16) + '\" text-anchor=\"middle\" font-size=\"11\" fill=\"#53697f\">' + escapeHtml(dateShort(r.date)) + '<\/text>';\n                }\n            });\n            holder.innerHTML = '<svg viewBox=\"0 0 ' + W + ' ' + H + '\" width=\"' + W + '\" height=\"' + H + '\" role=\"img\" aria-label=\"Dnevne oborine u zadnjih 30 dana\">' +\n                grid + bars + '<line x1=\"' + L + '\" x2=\"' + (W - R) + '\" y1=\"' + (H - B) + '\" y2=\"' + (H - B) + '\" stroke=\"#c9d6e2\"><\/line>' + labels +\n                '<text x=\"' + (L - 6) + '\" y=\"10\" text-anchor=\"end\" font-size=\"10\" fill=\"#8a9bab\">mm<\/text><\/svg>';\n\n            let html = rainKv('Ukupno (30 dana)', escapeHtml(fmt(total, 1)) + ' mm', true) +\n                       rainKv('Ki\u0161nih dana (\u22651 mm)', wet + rainDaysWord(wet) + ' od ' + last.length);\n            if (maxDay && maxDay.mm >= 0.1) html += rainKv('Najki\u0161niji dan', escapeHtml(fmt(maxDay.mm, 1) + ' mm \u00b7 ' + dateShort(maxDay.date)));\n            const cur = monthly && monthly.ok ? (monthly.months || []).find(m => m.current) : null;\n            if (cur && Number.isFinite(Number(cur.sum)) && Number.isFinite(Number(cur.normal))) {\n                const monthName = RAIN_MONTHS_FULL[Number(String(cur.ym).slice(5)) - 1] || cur.label;\n                html += rainKv('Ovaj mjesec do sada', escapeHtml(fmt(cur.sum, 1) + ' mm') + ' <small style=\"font-weight:400;color:#6f8398\">od prosje\u010dnih ' + escapeHtml(fmt(cur.normal, 0)) + ' mm za ' + escapeHtml(monthName) + '<\/small>');\n            }\n            return html;\n        }\n\n        function renderRain12(monthly) {\n            const holder = qs('rain-svg');\n            const months = monthly && monthly.ok ? (monthly.months || []) : [];\n            const covered = months.filter(m => m.sum !== null && m.sum !== undefined && Number.isFinite(Number(m.sum))).length;\n            if (!months.length || covered < 10) {\n                holder.innerHTML = '<div class=\"mv-rain-note\">Podaci za 12 mjeseci trenuta\u010dno nisu dovoljno potpuni za pouzdanu usporedbu.<\/div>';\n                return '';\n            }\n            const W = rainSvgWidth(holder), narrow = W < 480, H = 220, L = 38, R = 8, T = 22, B = 40;\n            const cw = (W - L - R) \/ months.length;\n            const maxV = niceMax(Math.max(...months.map(m => Math.max(Number(m.sum) || 0, Number(m.normal) || 0))));\n            const y = v => T + (H - T - B) * (1 - v \/ maxV);\n            let grid = '';\n            [0, maxV \/ 2, maxV].forEach(g => {\n                grid += '<line x1=\"' + L + '\" x2=\"' + (W - R) + '\" y1=\"' + y(g).toFixed(1) + '\" y2=\"' + y(g).toFixed(1) + '\" stroke=\"#e8eef4\"><\/line>' +\n                        '<text x=\"' + (L - 6) + '\" y=\"' + (y(g) + 4).toFixed(1) + '\" text-anchor=\"end\" font-size=\"11\" fill=\"#6f8398\">' + fmt(g, 0) + '<\/text>';\n            });\n            let bars = '', norms = '', labels = '', values = '';\n            let prevYear = null;\n            months.forEach((m, i) => {\n                const x = L + i * cw + cw * 0.18, w = cw * 0.64, cx = x + w \/ 2;\n                const raw = m.sum;\n                const v = (raw === null || raw === undefined) ? NaN : Number(raw);\n                if (Number.isFinite(v)) {\n                    const top = Math.min(y(v), H - B - 2);\n                    bars += '<rect x=\"' + x.toFixed(1) + '\" y=\"' + top.toFixed(1) + '\" width=\"' + w.toFixed(1) + '\" height=\"' + (H - B - top).toFixed(1) + '\" fill=\"' + (m.current ? '#b7d3ee' : '#4f93d1') + '\"><title>' +\n                        escapeHtml(m.label + ' ' + m.year + ': ' + fmt(v, 1) + ' mm' + (m.current ? ' (u tijeku)' : '') + (Number.isFinite(Number(m.normal)) ? ' \u00b7 prosjek ' + fmt(m.normal, 0) + ' mm' : '')) + '<\/title><\/rect>';\n                    values += '<text x=\"' + cx.toFixed(1) + '\" y=\"' + (top - 5).toFixed(1) + '\" text-anchor=\"middle\" font-size=\"' + (narrow ? 9.5 : 10.5) + '\" font-weight=\"600\" fill=\"#1b4b87\">' + fmt(v, 0) + '<\/text>';\n                }\n                const n = Number(m.normal);\n                if (Number.isFinite(n)) norms += '<line x1=\"' + (x - 2).toFixed(1) + '\" x2=\"' + (x + w + 2).toFixed(1) + '\" y1=\"' + y(n).toFixed(1) + '\" y2=\"' + y(n).toFixed(1) + '\" stroke=\"#16385f\" stroke-width=\"2.5\"><\/line>';\n                labels += '<text x=\"' + cx.toFixed(1) + '\" y=\"' + (H - B + 15) + '\" text-anchor=\"middle\" font-size=\"11\" fill=\"#53697f\">' + escapeHtml(m.label) + '<\/text>';\n                if (m.year !== prevYear) {\n                    labels += '<text x=\"' + cx.toFixed(1) + '\" y=\"' + (H - B + 29) + '\" text-anchor=\"middle\" font-size=\"10\" fill=\"#8a9bab\">' + m.year + '<\/text>';\n                    prevYear = m.year;\n                }\n            });\n            holder.innerHTML = '<svg viewBox=\"0 0 ' + W + ' ' + H + '\" width=\"' + W + '\" height=\"' + H + '\" role=\"img\" aria-label=\"Oborine po mjesecima za zadnjih 12 mjeseci, s vi\u0161egodi\u0161njim prosjekom\">' +\n                grid + bars + norms + values + '<line x1=\"' + L + '\" x2=\"' + (W - R) + '\" y1=\"' + (H - B) + '\" y2=\"' + (H - B) + '\" stroke=\"#c9d6e2\"><\/line>' + labels +\n                '<text x=\"' + (L - 6) + '\" y=\"10\" text-anchor=\"end\" font-size=\"10\" fill=\"#8a9bab\">mm<\/text><\/svg>';\n\n            const complete = months.filter(m => m.complete && Number.isFinite(Number(m.sum)));\n            const sum12 = months.reduce((a, m) => a + (Number(m.sum) || 0), 0);\n            const norm12 = months.reduce((a, m) => {\n                const n = Number(m.normal) || 0;\n                return a + (m.current ? n * (Number(m.days_expected) || 0) \/ (Number(m.days_in_month) || 30) : n);\n            }, 0);\n            let html = rainKv('Ukupno (12 mjeseci)', escapeHtml(fmt(sum12, 0)) + ' mm', true);\n            if (norm12 > 0) {\n                const pct = Math.round((sum12 \/ norm12 - 1) * 100);\n                const cls = pct >= 0 ? 'is-wet' : 'is-dry';\n                const word = pct === 0 ? 'u prosjeku' : (pct > 0 ? 'vi\u0161e od prosjeka' : 'manje od prosjeka');\n                html += rainKv('Prosjek za isto razdoblje', escapeHtml(fmt(norm12, 0)) + ' mm \u00b7 <span class=\"mv-rain-delta ' + cls + '\">' + (pct > 0 ? '+' : '') + pct + ' % ' + word + '<\/span>');\n            }\n            if (complete.length) {\n                const wettest = complete.reduce((a, b) => (Number(b.sum) > Number(a.sum) ? b : a));\n                const driest = complete.reduce((a, b) => (Number(b.sum) < Number(a.sum) ? b : a));\n                html += rainKv('Najki\u0161niji mjesec', escapeHtml(RAIN_MONTHS_FULL[Number(String(wettest.ym).slice(5)) - 1] + ' ' + wettest.year + ' \u00b7 ' + fmt(wettest.sum, 0) + ' mm'));\n                html += rainKv('Najsu\u0161niji mjesec', escapeHtml(RAIN_MONTHS_FULL[Number(String(driest.ym).slice(5)) - 1] + ' ' + driest.year + ' \u00b7 ' + fmt(driest.sum, 0) + ' mm'));\n            }\n            return html;\n        }\n\n        function renderRain(data) {\n            const chart = qs('rain-chart'), svg = qs('rain-svg'), stats = qs('rain-stats'), legend = qs('rain-legend'), sub = qs('rain-sub');\n            if (!chart || !svg || !stats) return;\n            const rows = rainDailyRows(data?.precip_history || {});\n            const monthly = data?.precip_monthly || null;\n            chart.hidden = rainRange !== '7d';\n            svg.hidden = rainRange === '7d';\n            let html = '';\n            if (rainRange === '7d') html = renderRain7(rows);\n            else if (rainRange === '30d') html = renderRain30(rows, monthly);\n            else html = renderRain12(monthly);\n            stats.innerHTML = html;\n            if (legend) legend.innerHTML = rainRange === '12m' ? rainLegendMonthlyHtml() : rainLegendDailyHtml();\n            if (sub) sub.textContent = rainRange === '7d' ? '\u2013 zadnjih 7 dana' : (rainRange === '30d' ? '\u2013 zadnjih 30 dana' : '\u2013 zadnjih 12 mjeseci');\n            root.querySelectorAll('[data-rain-range]').forEach(btn => {\n                const active = btn.getAttribute('data-rain-range') === rainRange;\n                btn.classList.toggle('is-active', active);\n                btn.setAttribute('aria-pressed', active ? 'true' : 'false');\n            });\n        }\n\n\n        function renderWindRose(directionDeg, speedKmh) {\n            const holder = qs('wind-rose');\n            if (!holder) return;\n            const deg = Number(directionDeg) || 0;\n            const b = beaufortFor(speedKmh);\n            const color = b ? beaufortColor(b.force) : '#3b82f6';\n            \/* 8 glavnih smjerova (ne samo N\/S\/E\/W), radijus 68 tako da label ne sije\u010de prsten. *\/\n            const compass = [['N',80,14],['NE',134,32],['E',146,80],['SE',134,128],['S',80,146],['SW',26,128],['W',14,80],['NW',26,32]];\n            const labels = compass.map(c => '<text x=\"' + c[1] + '\" y=\"' + c[2] + '\" text-anchor=\"middle\" dominant-baseline=\"middle\" font-size=\"12\" fill=\"#64748b\" font-weight=\"700\">' + c[0] + '<\/text>').join('');\n            holder.innerHTML =\n                '<svg class=\"mv-wind-svg\" viewBox=\"0 0 160 160\" aria-hidden=\"true\">' +\n                    '<circle cx=\"80\" cy=\"80\" r=\"54\" fill=\"none\" stroke=\"#e2e8f0\" stroke-width=\"2\"><\/circle>' +\n                    '<line x1=\"80\" y1=\"26\" x2=\"80\" y2=\"134\" stroke=\"#e2e8f0\"><\/line>' +\n                    '<line x1=\"26\" y1=\"80\" x2=\"134\" y2=\"80\" stroke=\"#e2e8f0\"><\/line>' +\n                    labels +\n                    '<g transform=\"rotate(' + deg + ' 80 80)\">' +\n                        '<line x1=\"80\" y1=\"80\" x2=\"80\" y2=\"30\" stroke=\"' + color + '\" stroke-width=\"6\" stroke-linecap=\"round\"><\/line>' +\n                        '<polygon points=\"80,16 70,36 90,36\" fill=\"' + color + '\"><\/polygon>' +\n                    '<\/g>' +\n                    '<circle cx=\"80\" cy=\"80\" r=\"6\" fill=\"' + color + '\"><\/circle>' +\n                '<\/svg>';\n        }\n\n        function renderClimate(c) {\n            qs('climate-subtitle').textContent = (c.location_label || 'Martinska Ves') + ' (' + (c.period || '') + ')';\n            qs('climate-month-a').textContent = c.month_label || '';\n            qs('climate-month-b').textContent = c.month_label || '';\n            qs('climate-month-c').textContent = c.month_label || '';\n            qs('climate-month-d').textContent = c.month_label || '';\n            qs('climate-month-e').textContent = c.month_label || '';\n            qs('climate-mean-temp').textContent = fmt(c.mean_temp, 1) + ' \u00b0C';\n            qs('climate-max-temp').textContent = fmt(c.max_temp, 1) + ' \u00b0C';\n            qs('climate-min-temp').textContent = fmt(c.min_temp, 1) + ' \u00b0C';\n            qs('climate-mean-precip').textContent = fmt(c.mean_precip_mm, 1) + ' mm';\n            qs('climate-sun-hours').textContent = fmt(c.sun_hours, 0) + ' h';\n            qs('climate-period').textContent = c.period || '\u2014';\n        }\n\n        \/* Sve postaje Save + Odra\/Kupa u jednom pozivu, za odabrani raspon. Koristi se i pri\n           prvom crtanju i pri promjeni raspona (klik na 24 sata\/3\/7\/14\/30 dana). *\/\n        function renderAllWater(data) {\n            renderWater('crnac', data.water?.sava?.crnac || data.water?.crnac);\n            renderWater('dubrovacak', data.water?.sava?.dubrovacak);\n            renderWater('rugvica', data.water?.sava?.rugvica || data.water?.rugvica);\n            renderWater('zagreb', data.water?.sava?.zagreb);\n            renderWater('slovenia', data.water?.sava?.slovenia);\n            applySavaRiseRanking(data.water?.sava || {});\n            renderSavaStrip(data.water?.sava || {}, '24h');\n            renderWater('odra', data.water?.odra_kupa?.odra);\n            renderWater('kupa', data.water?.odra_kupa?.kupa);\n            \/* Jednaka veli\u010dina velikog broja u svim karticama bloka: mjeri se prema\n               najduljem broju (s minusom), da \"cm\" i strelica uvijek stanu. *\/\n            root.querySelectorAll('.mv-water-wrap').forEach(wrap => {\n                let maxChars = 2;\n                wrap.querySelectorAll('.mv-water-level').forEach(el => { maxChars = Math.max(maxChars, Number(el.dataset.chars || 0)); });\n                wrap.style.setProperty('--mv-chars', maxChars);\n            });\n        }\n\n        function parseDhmzMeasured(st) {\n            if (!st) return null;\n            if (st.measured_at) { const d = new Date(st.measured_at); if (!isNaN(d.getTime())) return d; }\n            const m = String(st.display_time || '').match(\/(\\d{1,2})\\.\\s*(\\d{1,2})\\.\\s*(\\d{4})\\.?\\s*[\u00b7,\\s]\\s*(\\d{1,2})(?:\\s*[:.h]\\s*(\\d{2}))?\/);\n            if (!m) return null;\n            const d = new Date(Number(m[3]), Number(m[2]) - 1, Number(m[1]), Number(m[4]), m[5] ? Number(m[5]) : 0, 0);\n            return isNaN(d.getTime()) ? null : d;\n        }\n        function hhmm(d) { return String(d.getHours()).padStart(2, '0') + ':' + String(d.getMinutes()).padStart(2, '0'); }\n        function dhmzDayWord(d) {\n            const a = new Date(); a.setHours(0,0,0,0);\n            const b = new Date(d.getTime()); b.setHours(0,0,0,0);\n            const diff = Math.round((a - b) \/ 86400000);\n            if (diff === 0) return 'danas';\n            if (diff === 1) return 'ju\u010der';\n            return d.getDate() + '. ' + (d.getMonth() + 1) + '.';\n        }\n        function dhmzAgeText(min) {\n            if (min === null || !Number.isFinite(min)) return '';\n            if (min < 1) return 'manje od minute';\n            if (min < 60) return min + ' min';\n            const h = Math.floor(min \/ 60), r = min % 60;\n            return h + ' h' + (r ? ' ' + r + ' min' : '');\n        }\n\n        function renderAll(data) {\n            snapshotData = data;\n            places = Array.isArray(data.places) ? data.places : [];\n\n            const forecast = data.forecast || {};\n            const current = forecast.current || {};\n            const daily = forecast.daily || {};\n            const hourly = forecast.hourly || {};\n            const minutely15 = forecast.minutely_15 || {};\n            const aq = (data.air_quality || {}).current || {};\n            const snapshotAirLocation = data.air_quality_location || {slug:'martinska-ves', name:'Martinska Ves'};\n            setupAirLocations(data.air_locations || [], snapshotAirLocation.slug || 'martinska-ves');\n            const useSnapshotAir = selectedAirPlace === defaultAirPlace;\n\n            const updated = new Date(data.generated_at || Date.now());\n            qs('updated').textContent = updated.toLocaleString('hr-HR');\n\n            qs('now-icon').innerHTML = weatherIcon(current.weather_code, current.is_day);\n            const nowDesc = qs('now-desc');\n            if (nowDesc) nowDesc.textContent = Number.isFinite(Number(current.weather_code)) ? weatherDescription(current.weather_code) : '';\n            qs('temp').textContent = fmt(current.temperature_2m, 1);\n            qs('feels').textContent = fmt(current.apparent_temperature, 1);\n            qs('humidity').textContent = fmt(current.relative_humidity_2m, 0) + ' %';\n            qs('wind').textContent = windDirection(current.wind_direction_10m) + ' ' + fmt(current.wind_speed_10m, 0) + ' km\/h';\n            qs('pressure').textContent = fmt(current.pressure_msl, 0) + ' hPa';\n            qs('rain').textContent = fmt(daily.precipitation_sum?.[0], 1) + ' mm';\n\n            const dhmzSisak = data.dhmz_sisak || {};\n            const dhmzRef = qs('dhmz-sisak-ref');\n            const dhmzTemp = qs('dhmz-sisak-temp');\n            const dhmzTime = qs('dhmz-sisak-time');\n\n            function setDhmzRow(rowRole, valueRole, value) {\n                const row = qs(rowRole);\n                const valueEl = qs(valueRole);\n                const show = value !== null && value !== undefined && value !== '' && value !== '\u2014';\n                if (row) row.classList.toggle('is-visible', !!show);\n                if (valueEl && show) valueEl.textContent = value;\n                return !!show;\n            }\n\n            const dhmzHasTemp = Number.isFinite(Number(dhmzSisak.temperature_c));\n            const dhmzHasHumidity = Number.isFinite(Number(dhmzSisak.humidity_pct));\n            const dhmzHasPressure = Number.isFinite(Number(dhmzSisak.pressure_hpa));\n            const dhmzHasWind = Number.isFinite(Number(dhmzSisak.wind_speed_kmh));\n            const dhmzHasRain = Number.isFinite(Number(dhmzSisak.precip_24h_mm));\n            const dhmzHasAnyData = dhmzHasTemp || dhmzHasHumidity || dhmzHasPressure || dhmzHasWind || dhmzHasRain;\n\n            if (dhmzTemp) dhmzTemp.textContent = dhmzHasTemp ? fmt(Number(dhmzSisak.temperature_c), 1) + ' \u00b0C' : '\u2014';\n\n            setDhmzRow(\n                'dhmz-sisak-humidity-row',\n                'dhmz-sisak-humidity',\n                dhmzHasHumidity ? fmt(Number(dhmzSisak.humidity_pct), 0) + ' %' : null\n            );\n\n            const dhmzWind = dhmzHasWind\n                ? ((dhmzSisak.wind_direction || '').trim() ? String(dhmzSisak.wind_direction).trim() + ' ' : '') + fmt(Number(dhmzSisak.wind_speed_kmh), 0) + ' km\/h'\n                : null;\n            setDhmzRow('dhmz-sisak-wind-row', 'dhmz-sisak-wind', dhmzWind);\n\n            setDhmzRow(\n                'dhmz-sisak-pressure-row',\n                'dhmz-sisak-pressure',\n                dhmzHasPressure ? fmt(Number(dhmzSisak.pressure_hpa), 0) + ' hPa' : null\n            );\n\n            const hasRain24 = setDhmzRow(\n                'dhmz-sisak-rain-row',\n                'dhmz-sisak-rain',\n                dhmzHasRain ? fmt(Number(dhmzSisak.precip_24h_mm), 1) + ' mm' : null\n            );\n            const rainNote = qs('dhmz-sisak-rain-note');\n            if (rainNote) rainNote.classList.toggle('is-visible', hasRain24);\n\n            const dhmzAtEl = qs('dhmz-sisak-at');\n            const dhmzMeasured = parseDhmzMeasured(dhmzSisak);\n            const dhmzAgeMin = dhmzMeasured ? Math.max(0, Math.round((Date.now() - dhmzMeasured.getTime()) \/ 60000)) : null;\n            const dhmzStale = dhmzHasAnyData && (dhmzAgeMin !== null ? dhmzAgeMin >= 100 : !!dhmzSisak.fallback);\n            if (dhmzRef) dhmzRef.classList.toggle('is-stale', dhmzStale);\n            if (dhmzAtEl) dhmzAtEl.textContent = (dhmzHasTemp && dhmzMeasured) ? 'u ' + hhmm(dhmzMeasured) : '';\n            if (dhmzTime) {\n                if (dhmzHasAnyData) {\n                    if (dhmzMeasured) {\n                        const dayWord = dhmzDayWord(dhmzMeasured);\n                        dhmzTime.innerHTML = (dhmzStale ? 'Zadnje slu\u017ebeno mjerenje: ' : 'Slu\u017ebeno mjerenje: ')\n                            + escapeHtml(dayWord) + ' u <b>' + hhmm(dhmzMeasured) + '<\/b>'\n                            + ' \u00b7 prije ' + escapeHtml(dhmzAgeText(dhmzAgeMin))\n                            + ' \u00b7 DHMZ objavljuje jednom na sat';\n                    } else {\n                        const prefix = dhmzSisak.fallback ? 'Zadnje dostupno slu\u017ebeno mjerenje \u00b7 ' : 'Slu\u017ebeno mjerenje \u00b7 ';\n                        dhmzTime.textContent = dhmzSisak.display_time\n                            ? prefix + dhmzSisak.display_time\n                            : (dhmzSisak.fallback ? 'Zadnje dostupno slu\u017ebeno mjerenje' : 'Slu\u017ebeno referentno mjerenje');\n                    }\n                } else {\n                    dhmzTime.textContent = 'DHMZ Sisak \u00b7 podatak trenuta\u010dno nije dostupan';\n                }\n            }\n            if (dhmzRef) dhmzRef.classList.add('is-visible');\n\n            renderNext3Hours(minutely15);\n            renderDays(daily);\n            renderAllWater(data);\n            renderDubrovacakDetail(data);\n            renderWarnings(data.warnings || {});\n            renderDhmzRadar(data.radar_dhmz || {});\n            if (useSnapshotAir) {\n                renderAQI(aq);\n                renderPollenCard(aq);\n            }\n\n            let idx = 0;\n            if (Array.isArray(hourly.time) && current.time) {\n                const found = hourly.time.findIndex(t => t >= current.time);\n                idx = found >= 0 ? found : 0;\n            }\n            qs('soil-temp-6').textContent = fmt(Number(hourly.soil_temperature_6cm?.[idx]), 1) + ' \u00b0C';\n            qs('soil-temp-18').textContent = fmt(Number(hourly.soil_temperature_18cm?.[idx]), 1) + ' \u00b0C';\n            qs('soil-temp-54').textContent = fmt(Number(hourly.soil_temperature_54cm?.[idx]), 1) + ' \u00b0C';\n            qs('soil-moisture-27').textContent = fmt(Number(hourly.soil_moisture_9_to_27cm?.[idx]) * 100, 0) + ' % vol.';\n            qs('soil-moisture-81').textContent = fmt(Number(hourly.soil_moisture_27_to_81cm?.[idx]) * 100, 0) + ' % vol.';\n            qs('evapo').textContent = fmt(Number(daily.et0_fao_evapotranspiration?.[0]), 1) + ' mm';\n\n            renderUV(daily.uv_index_max?.[0]);\n            renderRain(data);\n            renderWindRose(current.wind_direction_10m, current.wind_speed_10m);\n\n            qs('wind-dir').textContent = windDirection(current.wind_direction_10m) + ' (' + fmt(current.wind_direction_10m, 0) + '\u00b0)';\n            qs('wind-speed').textContent = fmt(current.wind_speed_10m, 0) + ' km\/h';\n            qs('wind-gust').textContent = fmt(current.wind_gusts_10m, 0) + ' km\/h';\n            const windB = beaufortFor(current.wind_speed_10m);\n            qs('wind-desc').textContent = windB ? windB.force + ' Bf \u00b7 ' + windB.name : '\u2014';\n            const beaufortEl = qs('wind-beaufort');\n            if (beaufortEl) beaufortEl.innerHTML = beaufortGaugeHtml(current.wind_speed_10m);\n\n            const currentStamp = current.time ? 'Vrijeme podatka: ' + formatStamp(current.time) : 'Dohva\u0107eno: ' + formatStamp(data.generated_at);\n            const airStamp = aq.time ? 'Vrijeme podatka: ' + formatStamp(aq.time) : 'Dohva\u0107eno: ' + formatStamp(data.generated_at);\n            const soilStamp = hourly.time?.[idx] ? 'Vrijeme modela: ' + formatStamp(hourly.time[idx]) : 'Dohva\u0107eno: ' + formatStamp(data.generated_at);\n            const todayDate = daily.time?.[0] ? new Date(daily.time[0] + 'T12:00:00') : null;\n            const lastRainDate = data.precip_history?.daily?.time?.slice(-1)?.[0];\n\n            if (qs('weather-time')) qs('weather-time').textContent = currentStamp;\n            if (qs('nowcast-time')) qs('nowcast-time').textContent = 'Dohva\u0107eno: ' + formatStamp(data.generated_at);\n            if (qs('forecast-time')) qs('forecast-time').textContent = 'Dohva\u0107eno: ' + formatStamp(data.generated_at);\n            if (useSnapshotAir) {\n                if (qs('air-time')) qs('air-time').textContent = airStamp;\n                if (qs('pollen-time')) qs('pollen-time').textContent = airStamp;\n            }\n            if (qs('soil-time')) qs('soil-time').textContent = soilStamp;\n            if (qs('uv-time')) qs('uv-time').textContent = 'Dnevni maksimum za ' + (daily.time?.[0] ? dateShort(daily.time[0]) : 'danas');\n            if (qs('rain-history-time')) qs('rain-history-time').textContent = lastRainDate ? 'Zaklju\u010dno s ' + dateShort(lastRainDate) : '\u2014';\n            if (qs('wind-time')) qs('wind-time').textContent = currentStamp;\n\n            renderClimate(data.climate_reference || {});\n            renderPlaceLabels();\n        }\n\n        let dataLoadInFlight = false;\n        function loadData() {\n            if (dataLoadInFlight) return;\n            dataLoadInFlight = true;\n\n            const separator = endpoint.includes('?') ? '&' : '?';\n            const freshEndpoint = endpoint + separator + '_mv=' + Date.now();\n\n            fetch(freshEndpoint, {\n                method:'GET',\n                cache:'no-store',\n                credentials:'same-origin',\n                headers:{\n                    'Accept':'application\/json',\n                    'Cache-Control':'no-cache',\n                    'Pragma':'no-cache'\n                }\n            })\n            .then(r => r.ok ? r.json() : null)\n            .then(renderAll)\n            .catch(err => {\n                console.error('MV Meteo', err);\n                qs('updated').textContent = 'Podaci trenuta\u010dno nisu dostupni';\n            })\n            .finally(() => { dataLoadInFlight = false; });\n        }\n\n        root.addEventListener('change', function (event) {\n            const select = event.target.closest('[data-air-place-select]');\n            if (!select || !root.contains(select)) return;\n            const slug = String(select.value || '');\n            if (!airLocationBySlug(slug) || slug === selectedAirPlace) {\n                syncAirLocationControls();\n                return;\n            }\n            loadAirForPlace(slug);\n        });\n\n        \/* Vodostaji: prekida\u010d raspona (24 sata\/3\/7\/14\/30 dana) i skokovi na kartice \u2013 delegirano,\n           pa radi i nakon ponovnog crtanja. Promjena raspona stvarno prera\u010dunava traku toka,\n           retke promjene i graf u svakoj kartici (varijanta A), ne samo graf. *\/\n        root.addEventListener('click', function (event) {\n            const rangeBtn = event.target.closest('[data-water-range-btn]');\n            if (rangeBtn && root.contains(rangeBtn)) {\n                const range = WATER_RANGES[rangeBtn.getAttribute('data-water-range-btn')] ? rangeBtn.getAttribute('data-water-range-btn') : '24h';\n                if (root.dataset.waterRange === range) return;\n                root.dataset.waterRange = range;\n                root.querySelectorAll('[data-water-range-btn]').forEach(btn => {\n                    const active = btn.getAttribute('data-water-range-btn') === range;\n                    btn.classList.toggle('is-active', active);\n                    btn.setAttribute('aria-pressed', active ? 'true' : 'false');\n                });\n                if (snapshotData) renderAllWater(snapshotData, range);\n                return;\n            }\n            const dhmzJump = event.target.closest('[data-jump-dhmz-radar]');\n            if (dhmzJump && root.contains(dhmzJump)) {\n                const block = root.querySelector('[data-role=\"dhmz-radar\"]');\n                if (block) {\n                    scrollToWaterTarget(block);\n                    const playBtn = qs('dhmz-radar-play');\n                    if (playBtn && !playBtn.disabled && !dhmzRadarPlaying) startDhmzRadarAnimation();\n                }\n                return;\n            }\n            const cardRange = event.target.closest('[data-card-range]');\n            if (cardRange && root.contains(cardRange)) {\n                const box = cardRange.closest('.mv-water-box');\n                const r = cardRange.getAttribute('data-card-range');\n                if (!box || !WATER_RANGES[r]) return;\n                const key = String(box.getAttribute('data-role') || '').replace(\/^water-\/, '');\n                renderWater(key, waterStationByKey(key), r);\n                return;\n            }\n            const rainBtn = event.target.closest('[data-rain-range]');\n            if (rainBtn && root.contains(rainBtn)) {\n                const r = rainBtn.getAttribute('data-rain-range');\n                if (r === rainRange || !['7d','30d','12m'].includes(r)) return;\n                rainRange = r;\n                if (snapshotData) renderRain(snapshotData);\n                return;\n            }\n            const dubBtn = event.target.closest('[data-dub-range-btn]');\n            if (dubBtn && root.contains(dubBtn)) {\n                const r = dubBtn.getAttribute('data-dub-range-btn');\n                if (!WATER_RANGES[r] || r === dubRange) return;\n                dubRange = r;\n                if (snapshotData) renderDubrovacakDetail(snapshotData);\n                return;\n            }\n            const jump = event.target.closest('[data-sava-jump]');\n            if (jump && root.contains(jump)) {\n                scrollToWaterTarget(qs('water-' + jump.getAttribute('data-sava-jump')));\n                return;\n            }\n            const detail = event.target.closest('[data-jump-detail]');\n            if (detail && root.contains(detail)) {\n                scrollToWaterTarget(root.querySelector('.mv-card-dubrovacak-detail'));\n            }\n        });\n\n        const radarPlay = root.querySelector('[data-action=\"radar-play\"]');\n        if (radarPlay) radarPlay.addEventListener('click', toggleRadarAnimation);\n\n        const radarRange = qs('radar-range');\n        if (radarRange) radarRange.addEventListener('input', function () {\n            stopRadarAnimation();\n            if (!radarReady) return;\n            showRadarFrame(Number(radarRange.value));\n        });\n\n        root.querySelectorAll('[data-mapmode]').forEach(btn => {\n            btn.addEventListener('click', function () {\n                setMapMode(btn.getAttribute('data-mapmode') || 'temperature');\n            });\n        });\n\n        let attempts = 0;\n        const boot = setInterval(function () {\n            attempts++;\n            if (window.L) {\n                clearInterval(boot);\n                initMap();\n               loadData();\n\n\/* UI snapshot provjerava nove podatke svakih 10 sekundi. *\/\nsetInterval(loadData, 10 * 1000);\n\n\/* Lokalni sat u detaljnom Dubrov\u010dak bloku ide svake sekunde.\n   To NIJE vrijeme slu\u017ebenog hidrolo\u0161kog mjerenja. *\/\nupdateDubrovacakClock();\nsetInterval(updateDubrovacakClock, 1000);\n\n\/* Kad se korisnik vrati na stranicu na mobitelu *\/\ndocument.addEventListener('visibilitychange', function () {\n    if (document.visibilityState === 'visible') {\n        loadData();\n    }\n});\n\n\/* Dodatno osvje\u017ei pri povratku fokusa *\/\nwindow.addEventListener('focus', function () {\n    loadData();\n});\n            }\n            if (attempts > 50) {\n                clearInterval(boot);\n                qs('updated').textContent = 'Leaflet se nije u\u010ditao';\n            }\n        }, 100);\n    })();\n    <\/script>\n<\/div>\n<\/div>\n<div class=\"dj-section dj-full\">\n<div class=\"dj-in\">\n<h2>\u0160to dobivate<\/h2>\n<p><span class=\"dj-tag\">Web GIS<\/span><span class=\"dj-tag\">Smart Community<\/span><span class=\"dj-tag\">Digitalne javne usluge<\/span><\/p>\n<div class=\"dj-features\">\n<div>\n<h3>Ustanove i javne slu\u017ebe<\/h3>\n<p>Op\u0107ina ili grad, \u0161kole, vrti\u0107i, ambulante, po\u0161ta i udruge s kontaktima i radnim vremenom.<\/p>\n<\/div>\n<div>\n<h3>Znamenitosti i va\u017ene to\u010dke<\/h3>\n<p>Crkve, kapelice, spomenici, sportski objekti, mostovi i skele.<\/p>\n<\/div>\n<div>\n<h3>Javni prijevoz<\/h3>\n<p>Stajali\u0161ta i polasci autobusa, uz prikaz u stvarnom vremenu.<\/p>\n<\/div>\n<div>\n<h3>\u0160kolski prijevoz<\/h3>\n<p>Zaseban sloj za \u0161kolske linije i stajali\u0161ta.<\/p>\n<\/div>\n<div>\n<h3>Vrijeme i vodostaj<\/h3>\n<p>Prognoza po naseljima, stanje rijeka i slu\u017ebena upozorenja.<\/p>\n<\/div>\n<div>\n<h3>Tra\u017eilo<\/h3>\n<p>Brzo pronala\u017eenje mjesta, ulica, ustanova i pojmova na karti.<\/p>\n<\/div>\n<\/div>\n<\/div>\n<\/div>\n<div class=\"dj-split dj-split--rev\">\n<div>\n<h2>Za gra\u0111ane i za op\u0107inu<\/h2>\n<div class=\"dj-features\" style=\"grid-template-columns:1fr;margin-top:20px\">\n<div>\n<h3>Bez posla za djelatnike<\/h3>\n<p>Podatke prikupljamo i odr\u017eavamo mi \u2013 djelatnici ne moraju u\u010diti novi sustav ni unositi podatke.<\/p>\n<\/div>\n<div>\n<h3>Bez aplikacije<\/h3>\n<p>Radi u web pregledniku na mobitelu i ra\u010dunalu \u2013 jednostavno i za starije gra\u0111ane.<\/p>\n<\/div>\n<div>\n<h3>Va\u0161 vizualni identitet<\/h3>\n<p>Boje, grb i stil karte prilago\u0111eni op\u0107ini, gradu ili \u017eupaniji.<\/p>\n<\/div>\n<div>\n<h3>Na va\u0161oj web stranici<\/h3>\n<p>Karta se ugra\u0111uje u postoje\u0107u stranicu op\u0107ine, grada ili \u017eupanije.<\/p>\n<\/div>\n<div>\n<h3>Povezano s javnim prijevozom<\/h3>\n<p>Klik na stajali\u0161te otvara polaske sa semafora Digitalna JS.<\/p>\n<\/div>\n<\/div>\n<\/div>\n<div><img decoding=\"async\" src=\"https:\/\/digitalna.hr\/wp-content\/uploads\/2026\/10\/Gemini_Generated_Image_j24i9rj24i9rj24i-1536x1147.jpg\" alt=\"Interaktivna karta i mobilni semafor na ra\u010dunalu, mobitelu i velikom ekranu u uredu op\u0107ine\" width=\"1536\" height=\"1147\" loading=\"lazy\"><\/div>\n<\/div>\n<div class=\"dj-section dj-full\">\n<div class=\"dj-in\">\n<h2>Kako izgleda uvo\u0111enje<\/h2>\n<div class=\"dj-features\">\n<div>\n<h3>1. Dogovor sadr\u017eaja<\/h3>\n<p>Zajedno odredimo koji slojevi i podaci idu na kartu.<\/p>\n<\/div>\n<div>\n<h3>2. Prikupljanje podataka<\/h3>\n<p>Na terenu i iz javnih izvora prikupimo i provjerimo sve lokacije i informacije.<\/p>\n<\/div>\n<div>\n<h3>3. Izrada i ugradnja<\/h3>\n<p>Pripremimo kartu u va\u0161em vizualnom identitetu i postavimo je na va\u0161u web stranicu.<\/p>\n<\/div>\n<div>\n<h3>4. Odr\u017eavanje<\/h3>\n<p>Podatke redovito a\u017euriramo i dodajemo nove slojeve \u2013 bez posla za va\u0161e djelatnike.<\/p>\n<\/div>\n<\/div>\n<\/div>\n<\/div>\n<div class=\"dj-cta\">\n<h2>\u017delite kartu za svoju op\u0107inu ili grad?<\/h2>\n<p>Pokazat \u0107emo vam kartu koja ve\u0107 radi i predlo\u017eiti sadr\u017eaj i slojeve za va\u0161e podru\u010dje.<\/p>\n<p class=\"dj-btns\"><a class=\"dj-btn\" href=\"\/index.php\/kontakt\/\">Zatra\u017eite ponudu<\/a><a class=\"dj-btn dj-btn--alt\" href=\"\/index.php\/kako-do-rjesenja\/\">Kako do rje\u0161enja<\/a><\/p>\n<\/div>\n<h2>Sustavi javnog prijevoza<\/h2>\n<div class=\"dj-links\"><a href=\"\/index.php\/javni-prijevoz\/\"><span class=\"dj-ico\"><svg width=\"18\" height=\"18\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><rect x=\"4\" y=\"3\" width=\"16\" height=\"15\" rx=\"2\"\/><path d=\"M4 11h16M8 21v-3M16 21v-3\"\/><\/svg><\/span>Javni prijevoz<\/a><a href=\"\/index.php\/javni-prijevoz\/mobilni-semafor\/\"><span class=\"dj-ico\"><svg width=\"18\" height=\"18\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><rect x=\"6\" y=\"2\" width=\"12\" height=\"20\" rx=\"2\"\/><path d=\"M11 18h2\"\/><\/svg><\/span>Mobilni semafor<\/a><a href=\"\/index.php\/javni-prijevoz\/veliki-semafor\/\"><span class=\"dj-ico\"><svg width=\"18\" height=\"18\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><rect x=\"2\" y=\"4\" width=\"20\" height=\"13\" rx=\"2\"\/><path d=\"M8 21h8M12 17v4\"\/><\/svg><\/span>Veliki semafor<\/a><a href=\"\/index.php\/javni-prijevoz\/detekcija-stajalista\/\"><span class=\"dj-ico\"><svg width=\"18\" height=\"18\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><path d=\"M12 22s7-6.5 7-12a7 7 0 0 0-14 0c0 5.5 7 12 7 12z\"\/><circle cx=\"12\" cy=\"10\" r=\"2.5\"\/><\/svg><\/span>Detekcija stajali\u0161ta<\/a><a href=\"\/index.php\/javni-prijevoz\/qr-naljepnice\/\"><span class=\"dj-ico\"><svg width=\"18\" height=\"18\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><rect x=\"3\" y=\"3\" width=\"7\" height=\"7\"\/><rect x=\"14\" y=\"3\" width=\"7\" height=\"7\"\/><rect x=\"3\" y=\"14\" width=\"7\" height=\"7\"\/><path d=\"M14 14h3v3h-3zM17 20h4v-3\"\/><\/svg><\/span>QR naljepnice<\/a><\/div>\n<div class=\"dj-footer dj-full\">\n<div class=\"dj-in\">\n<div class=\"dj-footer__grid\">\n<div>  <a href=\"\/\"><img loading=\"lazy\" decoding=\"async\" class=\"dj-footer__logo\" src=\"\/wp-content\/uploads\/2026\/10\/digitalna-hr-logo-svijetli.png\" alt=\"Digitalna HR\" width=\"600\" height=\"110\" \/><\/a>  Programska rje\u0161enja za jedinice lokalne samouprave \u2013 interaktivne karte i sustavi za javni prijevoz.  <\/div>\n<div>\n<h4>Rje\u0161enja<\/h4>\n<p> <a href=\"\/index.php\/javni-prijevoz\/\">Javni prijevoz<\/a><a href=\"\/index.php\/interaktivna-karta\/\">Interaktivna karta<\/a><a href=\"\/index.php\/javni-prijevoz\/mobilni-semafor\/\">Mobilni semafor<\/a><a href=\"\/index.php\/javni-prijevoz\/veliki-semafor\/\">Veliki semafor<\/a>  <\/div>\n<div>\n<h4>Informacije<\/h4>\n<p> <a href=\"\/index.php\/kako-do-rjesenja\/\">Kako do rje\u0161enja<\/a><a href=\"\/index.php\/reference\/\">Reference<\/a><a href=\"\/index.php\/kontakt\/\">Kontakt<\/a>  <\/div>\n<\/p><\/div>\n<div class=\"dj-footer__bot\">\u00a9 2026 Digitalna JS. Sva prava pridr\u017eana.<\/div>\n<\/p><\/div>\n<\/p><\/div>\n","protected":false},"excerpt":{"rendered":"<p>Digitalno sredi\u0161te va\u0161e op\u0107ine, grada ili \u017eupanije \u2013 na jednoj karti. Interaktivna karta okuplja na jednom mjestu sve \u0161to gra\u0111ani i posjetitelji tra\u017ee: ustanove, usluge, znamenitosti, javni prijevoz i korisne informacije. Jedinica lokalne samouprave time dobiva moderan i pregledan kanal komunikacije koji radi na mobitelu i na ra\u010dunalu. Zatra\u017eite ponuduIsprobajte kartu u\u017eivo \u2193 Problem Informacije [&hellip;]<\/p>\n","protected":false},"author":1,"featured_media":0,"parent":0,"menu_order":3,"comment_status":"closed","ping_status":"closed","template":"","meta":{"footnotes":""},"class_list":["post-165","page","type-page","status-publish"],"_links":{"self":[{"href":"https:\/\/digitalna.hr\/index.php\/wp-json\/wp\/v2\/pages\/165","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/digitalna.hr\/index.php\/wp-json\/wp\/v2\/pages"}],"about":[{"href":"https:\/\/digitalna.hr\/index.php\/wp-json\/wp\/v2\/types\/page"}],"author":[{"embeddable":true,"href":"https:\/\/digitalna.hr\/index.php\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/digitalna.hr\/index.php\/wp-json\/wp\/v2\/comments?post=165"}],"version-history":[{"count":24,"href":"https:\/\/digitalna.hr\/index.php\/wp-json\/wp\/v2\/pages\/165\/revisions"}],"predecessor-version":[{"id":455,"href":"https:\/\/digitalna.hr\/index.php\/wp-json\/wp\/v2\/pages\/165\/revisions\/455"}],"wp:attachment":[{"href":"https:\/\/digitalna.hr\/index.php\/wp-json\/wp\/v2\/media?parent=165"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}