from flask import Flask, request, session, redirect import html import sqlite3 from pathlib import Path app = Flask(__name__) app.secret_key = "geheimnis-aus-dem-weltall" DB_PATH = Path(__file__).with_name("adventure.db") def get_db(): db = sqlite3.connect(DB_PATH) db.row_factory = sqlite3.Row return db BASE_CSS = """ :root { color-scheme: dark; } * { box-sizing: border-box; } body { margin: 0; font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif; background: linear-gradient(135deg, #07121d 0%, #102a43 45%, #1e3a5f 100%); color: #e2e8f0; min-height: 100vh; } .shell { min-height: 100vh; display: grid; place-items: center; padding: 2rem 1rem; } .card { width: min(760px, 100%); background: rgba(7, 18, 29, 0.88); border: 1px solid rgba(148, 163, 184, 0.25); border-radius: 24px; padding: 2rem; box-shadow: 0 20px 60px rgba(0, 0, 0, 0.35); backdrop-filter: blur(10px); } .card h1 { margin-top: 0; margin-bottom: 0.75rem; font-size: 2rem; color: #f8fafc; } .card p { line-height: 1.7; color: #cbd5e1; } .actions, .links { display: flex; flex-wrap: wrap; gap: 0.75rem; margin-top: 1.25rem; } .btn, .card a, .card button { display: inline-block; background: linear-gradient(135deg, #2563eb 0%, #06b6d4 100%); color: #f8fafc; border: none; border-radius: 999px; padding: 0.8rem 1.1rem; text-decoration: none; font-weight: 700; cursor: pointer; transition: transform 0.2s ease, box-shadow 0.2s ease; box-shadow: 0 10px 25px rgba(6, 182, 212, 0.25); } .btn:hover, .card a:hover, .card button:hover { transform: translateY(-2px); box-shadow: 0 12px 30px rgba(37, 99, 235, 0.35); } .btn.secondary { background: linear-gradient(135deg, #475569 0%, #64748b 100%); box-shadow: 0 10px 25px rgba(100, 116, 139, 0.25); } form { display: flex; flex-wrap: wrap; gap: 0.75rem; align-items: center; margin-top: 1rem; } input { flex: 1 1 220px; border: 1px solid rgba(148, 163, 184, 0.35); border-radius: 999px; padding: 0.8rem 1rem; background: rgba(15, 23, 42, 0.9); color: #f8fafc; } input:focus { outline: 2px solid rgba(6, 182, 212, 0.45); border-color: transparent; } """ BASE_JS = """ window.addEventListener('DOMContentLoaded', () => { const firstInput = document.querySelector('input'); if (firstInput) firstInput.focus(); }); """ def render_page(title, body_html): return f""" {html.escape(title)}
{body_html}
""" @app.route("/", methods=["GET", "POST"]) @app.route("/app", methods=["GET", "POST"]) @app.route("/app/", methods=["GET", "POST"]) def start(): if request.method == "POST": # Formular abgeschickt? name = request.form["name"].strip() if name != "": session["spieler"] = name # App merkt sich: das bist du db = get_db() db.execute( "INSERT OR IGNORE INTO spielstand (spieler, raum_id) VALUES (?, 1)", (name,) ) db.commit() db.close() return redirect("/app/raum/1") html = '

Verlies

' if "spieler" in session: db = get_db() s = db.execute( "SELECT raum_id FROM spielstand WHERE spieler=?", (session["spieler"],) ).fetchone() db.close() if s: html = html + '

Willkommen zurück, ' + html.escape(session["spieler"]) + '!

' \ + 'Weiterspielen
' return html + '
Dein Name: ' \ + '
' @app.route("/raum/", methods=["GET", "POST"]) @app.route("/app/raum/", methods=["GET", "POST"]) def raum(id): db = get_db() if "spieler" in session: # angemeldet? db.execute( "UPDATE spielstand SET raum_id=? WHERE spieler=?", (id, session["spieler"]) ) db.commit() r = db.execute("SELECT * FROM raeume WHERE id=?", (id,)).fetchone() if not r: db.close() return render_page( "Raum nicht gefunden", '

Raum nicht gefunden

Der angeforderte Raum existiert nicht.

' ) if r["raetsel_frage"]: if request.method == "POST": if request.form.get("antwort", "").strip() == r["raetsel_antwort"]: db.close() return render_page( "Notsignal aktiviert", '

Notsignal erfolgreich aktiviert

Rettung ist unterwegs.

' ) db.close() return render_page( "Falscher Code", '

Falscher Code

Der KI-Kern reagiert nicht.

' ) db.close() body = f"""

{html.escape(r['name'])}

{html.escape(r['beschreibung'])}

""" return render_page(html.escape(r["name"]), body) ausgaenge = db.execute( "SELECT richtung, nach_raum FROM ausgaenge WHERE von_raum=?", (id,) ).fetchall() db.close() body = f"""

{html.escape(r['name'])}

{html.escape(r['beschreibung'])}

""" if "spieler" in session: body = body + '

Unterwegs als: ' + html.escape(session["spieler"]) + '

' body = body + """ " return render_page(html.escape(r["name"]), body) @app.route("/reset") @app.route("/app/reset") def reset(): session.pop("spieler", None) return redirect("/app/") if __name__ == "__main__": app.run(host="0.0.0.0", port=9004)