document.getElementById("open-fin-modal").addEventListener("click", function() { document.getElementById("fin-modal").style.visibility = "visible"; }); document.querySelectorAll(".close-fin-modal").forEach(function(button) { button.addEventListener("click", function() { document.getElementById("fin-modal").style.visibility = "hidden"; }); }); document.getElementById("open-game-modal").addEventListener("click", function() { document.getElementById("game-modal").style.visibility = "visible"; }); document.querySelectorAll(".close-game-modal").forEach(function(button) { button.addEventListener("click", function() { document.getElementById("game-modal").style.visibility = "hidden"; }); }); document.getElementById("toggle-collapse").addEventListener("click", function() { const collapseDiv = document.getElementById("page-collapse"); if (collapseDiv.style.visibility === "visible") { collapseDiv.style.visibility = "hidden"; } else { collapseDiv.style.visibility = "visible"; } }); // Igra const gameState = { active: false, loading: false, currentEntry: null, normalizedAnswer: "", attemptsLeft: 3, roundPoints: 100, score: 0, correct: 0, failed: 0, guesses: 0, currentWordGuessed: false }; const gameElements = {}; function stripHtmlTags(html) { return String(html || "") .replace(/<\s*br\s*\/?>/gi, "\n") .replace(/<\s*\/p\s*>/gi, "\n") .replace(/<\s*p[^>]*>/gi, "") .replace(/<[^>]+>/g, "") .replace(/ /g, " ") .replace(/&/g, "&") .replace(/</g, "<") .replace(/>/g, ">") .replace(/"/g, '"') .replace(/'/g, "'") .replace(/\n{3,}/g, "\n\n") .trim(); } function normalizeGuess(value) { return String(value || "") .toLowerCase() .normalize("NFD") .replace(/[\u0300-\u036f]/g, "") .replace(/\s+/g, "") .trim(); } function parseDefinitions(html) { const plain = stripHtmlTags(html); return plain .split(/\n+/) .map(line => line.trim()) .filter(Boolean); } function setGameMessage(message, type) { if (!gameElements.feedback) { return; } gameElements.feedback.textContent = message; gameElements.feedback.classList.remove("is-success", "is-error", "is-neutral"); gameElements.feedback.classList.add(type || "is-neutral"); } function updateGameStats() { if (gameElements.attemptsLeft) { gameElements.attemptsLeft.textContent = String(gameState.attemptsLeft); } if (gameElements.roundPoints) { gameElements.roundPoints.textContent = String(gameState.roundPoints); } if (gameElements.score) { gameElements.score.textContent = String(gameState.score); } if (gameElements.correct) { gameElements.correct.textContent = String(gameState.correct); } if (gameElements.failed) { gameElements.failed.textContent = String(gameState.failed); } if (gameElements.guesses) { gameElements.guesses.textContent = String(gameState.guesses); } } function setGameScreen(screen) { const screens = ["start", "play", "stats"]; screens.forEach(name => { const element = gameElements[`${name}Screen`]; if (element) { element.hidden = name !== screen; } }); } function resetRoundState() { gameState.loading = false; gameState.attemptsLeft = 3; gameState.roundPoints = 100; gameState.currentWordGuessed = false; updateGameStats(); setGameMessage("", "is-neutral"); if (gameElements.guessInput) { gameElements.guessInput.value = ""; gameElements.guessInput.disabled = false; gameElements.guessInput.focus(); } if (gameElements.submitGuessButton) { gameElements.submitGuessButton.disabled = false; } } function renderCurrentEntry(entry) { const definitions = parseDefinitions(entry?.Vsebina); const typeText = entry?.Tip || "-"; if (gameElements.wordType) { gameElements.wordType.textContent = typeText; } if (gameElements.definitions) { if (!definitions.length) { gameElements.definitions.innerHTML = '

Opis za ta vnos ni na voljo.

'; } else { gameElements.definitions.innerHTML = definitions .map(definition => `
${definition}
`) .join(""); } } gameState.currentEntry = entry; gameState.normalizedAnswer = normalizeGuess(entry?.Kljuc); resetRoundState(); } function showGameStats() { if (gameElements.statScore) { gameElements.statScore.textContent = String(gameState.score); } if (gameElements.statCorrect) { gameElements.statCorrect.textContent = String(gameState.correct); } if (gameElements.statFailed) { gameElements.statFailed.textContent = String(gameState.failed); } if (gameElements.statGuesses) { gameElements.statGuesses.textContent = String(gameState.guesses); } setGameScreen("stats"); } function nextWord() { if (!gameState.active) { return; } gameState.loading = true; setGameMessage("Nalagam nov vnos ...", "is-neutral"); fetch("https://ssnj.dcrubro.com/api/random-vnos", { method: "GET" }) .then(response => { if (!response.ok) { throw new Error(`HTTP ${response.status}`); } return response.json(); }) .then(data => { if (!data || !data.success || !data.data) { throw new Error("Neveljaven odgovor strežnika"); } renderCurrentEntry(data.data); setGameScreen("play"); setGameMessage("Ugibajte besedo glede na definicijo.", "is-neutral"); }) .catch(error => { console.error("random-vnos error", error); setGameMessage("Napaka pri nalaganju novega vnosa. Poskusite znova.", "is-error"); gameState.loading = false; }) .finally(() => { gameState.loading = false; }); } function finishCurrentWord(correctlyGuessed) { if (correctlyGuessed) { gameState.correct += 1; } else { gameState.failed += 1; gameState.score = Math.max(0, gameState.score - 30); } updateGameStats(); if (gameElements.guessInput) { gameElements.guessInput.value = ""; } setTimeout(() => { if (gameState.active) { nextWord(); } }, 700); } function submitGuess() { if (!gameState.active || gameState.loading || !gameState.currentEntry) { return; } const guess = normalizeGuess(gameElements.guessInput ? gameElements.guessInput.value : ""); if (!guess) { setGameMessage("Vnesite svoj ugib.", "is-error"); return; } gameState.guesses += 1; updateGameStats(); if (guess === gameState.normalizedAnswer) { gameState.currentWordGuessed = true; gameState.score += gameState.roundPoints; setGameMessage(`Pravilno. Rešitev je ${gameState.currentEntry.Kljuc}.`, "is-success"); updateGameStats(); finishCurrentWord(true); return; } gameState.attemptsLeft -= 1; gameState.roundPoints = gameState.attemptsLeft === 2 ? 50 : gameState.attemptsLeft === 1 ? 25 : 0; updateGameStats(); if (gameState.attemptsLeft > 0) { setGameMessage(`Napačno. Preostali poskusi: ${gameState.attemptsLeft}.`, "is-error"); if (gameElements.guessInput) { gameElements.guessInput.value = ""; gameElements.guessInput.focus(); } return; } setGameMessage(`Tudi tretji poskus ni uspel. Rešitev je ${gameState.currentEntry.Kljuc}.`, "is-error"); finishCurrentWord(false); } function startGame() { gameState.active = true; gameState.score = 0; gameState.correct = 0; gameState.failed = 0; gameState.guesses = 0; updateGameStats(); setGameScreen("play"); nextWord(); } function bindGameElements() { gameElements.startScreen = document.getElementById("game-start-screen"); gameElements.playScreen = document.getElementById("game-play-screen"); gameElements.statsScreen = document.getElementById("game-stats-screen"); gameElements.wordType = document.getElementById("game-word-type"); gameElements.definitions = document.getElementById("game-definitions"); gameElements.guessInput = document.getElementById("game-guess-input"); gameElements.submitGuessButton = document.getElementById("submit-guess-button"); gameElements.restartGameButton = document.getElementById("restart-game-button"); gameElements.feedback = document.getElementById("game-feedback"); gameElements.attemptsLeft = document.getElementById("game-attempts-left"); gameElements.roundPoints = document.getElementById("game-round-points"); gameElements.score = document.getElementById("game-stat-score"); gameElements.correct = document.getElementById("game-stat-correct"); gameElements.failed = document.getElementById("game-stat-failed"); gameElements.guesses = document.getElementById("game-stat-guesses"); gameElements.statScore = document.getElementById("game-stat-score"); gameElements.statCorrect = document.getElementById("game-stat-correct"); gameElements.statFailed = document.getElementById("game-stat-failed"); gameElements.statGuesses = document.getElementById("game-stat-guesses"); } bindGameElements(); document.getElementById("start-game-button").addEventListener("click", startGame); document.getElementById("submit-guess-button").addEventListener("click", submitGuess); document.getElementById("restart-game-button").addEventListener("click", startGame); document.getElementById("game-guess-input").addEventListener("keydown", function(event) { if (event.key === "Enter") { event.preventDefault(); submitGuess(); } }); // Konec igre // Davčne stopnje in razredi za leto 2025 const taxBrackets = [ { razred: 1, min: 0, max: 9210.26, rate: 16 }, { razred: 2, min: 9210.26, max: 27089.00, rate: 26 }, { razred: 3, min: 27089.00, max: 54178.00, rate: 33 }, { razred: 4, min: 54178.00, max: 78016.32, rate: 39 }, { razred: 5, min: 78016.32, max: Infinity, rate: 50 } ]; const STANDARD_DEDUCTION = 5551.93; function parseEurAmount(input) { if (!input) return null; // Remove spaces, replace . with empty (thousands separator) and , with . (decimal) let normalized = input.trim().replace(/\s/g, "").replace(/\./g, "").replace(",", "."); let num = parseFloat(normalized); return isNaN(num) ? null : num; } function formatEurAmount(num) { // Format with thousands separator (.) and decimal separator (,) return num.toFixed(2).replace(".", ",").replace(/\B(?=(\d{3})+(?!\d))/g, "."); } function calculateTaxBracket(amount) { for (let bracket of taxBrackets) { if (amount >= bracket.min && amount < bracket.max) { return bracket; } } return taxBrackets[taxBrackets.length - 1]; // Return highest bracket } function calculateProgressiveTax(amount) { let totalTax = 0; for (let bracket of taxBrackets) { if (amount <= bracket.min) { break; } let upperLimit = Math.min(amount, bracket.max); let taxableInBracket = upperLimit - bracket.min; totalTax += taxableInBracket * (bracket.rate / 100); } return totalTax; } function updateCalculator() { const amountInput = document.getElementById("amount-input").value; const useDeduction = document.getElementById("deduction-checkbox").checked; const resultDiv = document.getElementById("calculator-result"); let amount = parseEurAmount(amountInput); if (amount === null || amount < 0) { resultDiv.style.display = "none"; return; } let taxBasis = amount; if (useDeduction && amount > STANDARD_DEDUCTION) { taxBasis = amount - STANDARD_DEDUCTION; } const bracket = calculateTaxBracket(taxBasis); const taxAmount = calculateProgressiveTax(taxBasis); document.getElementById("result-razred").textContent = bracket.razred; document.getElementById("result-rate").textContent = bracket.rate + " %"; document.getElementById("result-basis").textContent = formatEurAmount(taxBasis) + " EUR"; document.getElementById("result-tax").textContent = formatEurAmount(taxAmount) + " EUR"; resultDiv.style.display = "block"; } document.getElementById("amount-input").addEventListener("input", updateCalculator); document.getElementById("deduction-checkbox").addEventListener("change", updateCalculator);