diff --git a/README.md b/README.md index e1f8429..0b56123 100644 --- a/README.md +++ b/README.md @@ -39,3 +39,18 @@ Odštampani PDF-ovi ostaju u `~/.local/share/idriz/out/`. ``` IDRIZ_DRY_RUN=1 .venv/bin/python scripts/test_summary.py "Volcano" "8 godina" ``` + +## Igra "Superheroji" + +Glasovna igra (bez štampanja). Tok: Idriz pita koliko igrača (1–5) i imena, pa se +igra nekoliko rundi. Svaku rundu svaki igrač kaže jednog izmišljenog lika (bilo koji +medij — Supermen, Mario, La Linea, Mad Max...), a Idriz presudi ko bi pobijedio i +zašto. Pobjednik runde se više ne može birati do kraja partije. Sistem pamti +relativne jačine likova (Elo) u `~/.local/share/idriz/heroes.json` da borbe budu +dosljedne kroz partije. Za prepoznavanje likova koristi se najjači tekstualni model +(`game_model`, default `gpt-5.5`) i njegovo znanje; web search (Responses API) samo +kad model ne zna lika. + +- `idriz/gamestore.py` — trajno skladište (heroji, Elo, broj rundi), bez vanjskih zavisnosti. +- `idriz/game.py` — prepoznavanje likova, presuđivanje, tok partije (`Match`). +- Broj rundi i rang-lista heroja se podešavaju u admin panelu (tab "Superheroji"). diff --git a/admin/app.py b/admin/app.py index d2adb55..3d64c35 100644 --- a/admin/app.py +++ b/admin/app.py @@ -7,14 +7,20 @@ Prijava ide preko PAM-a (Linux korisnik `idriz`). import os import secrets import subprocess +import sys from datetime import datetime from functools import wraps +from pathlib import Path import pam as pam_module from flask import ( Flask, render_template, request, redirect, url_for, session, flash ) +# Pristup skladištu igre (bez openai zavisnosti) iz glavnog idriz paketa. +sys.path.insert(0, str(Path(__file__).resolve().parent.parent)) +from idriz import gamestore # noqa: E402 + # --- Konfiguracija ----------------------------------------------------------- # Samo ovaj Linux korisnik smije da se prijavi. @@ -195,6 +201,37 @@ def status(): ) +@app.route("/superheroji", methods=["GET", "POST"]) +@login_required +def superheroji(): + if request.method == "POST": + action = request.form.get("action") + if action == "rounds": + try: + n = int(request.form.get("rounds", "")) + saved = gamestore.save_rounds(n) + flash(f"Broj rundi postavljen na {saved}.") + except (ValueError, TypeError): + flash("Neispravan broj rundi.") + elif action == "reset": + store = gamestore.HeroStore() + store.heroes = {} + store.aliases = {} + store.save() + flash("Pamćenje jačina heroja je obrisano.") + return redirect(url_for("superheroji")) + + store = gamestore.HeroStore() + return render_template( + "superheroji.html", + rounds=gamestore.load_rounds(), + min_rounds=gamestore.MIN_ROUNDS, + max_rounds=gamestore.MAX_ROUNDS, + heroes=store.leaderboard(), + active_page="superheroji", + ) + + if __name__ == "__main__": from waitress import serve print(f"Idriz admin na http://{LISTEN_HOST}:{LISTEN_PORT}") diff --git a/admin/templates/base.html b/admin/templates/base.html index 0a27a15..f17ec47 100644 --- a/admin/templates/base.html +++ b/admin/templates/base.html @@ -98,6 +98,9 @@ ● Status servisa + + ★ Superheroji +