erster funktioniertender Draft

This commit is contained in:
FDS 2026-01-05 14:38:43 +01:00
parent de8dbd6b28
commit 58b2e32f90
8 changed files with 401 additions and 73 deletions

View file

@ -1,9 +1,182 @@
/* Basis-Stile */ /* Basis-Stile */
:root {
--primary-color: #4361ee;
--primary-hover: #3a56d4;
--secondary-color: #3f37c9;
--accent-color: #4895ef;
--light-color: #f8f9fa;
--dark-color: #212529;
--success-color: #4cc9f0;
--border-radius: 8px;
--box-shadow: 0 4px 6px rgba(0, 0, 0, 0.1);
--transition: all 0.3s ease;
}
body { body {
font-family: Arial, sans-serif; font-family: 'Segoe UI', Roboto, 'Helvetica Neue', sans-serif;
margin: 0; margin: 0;
padding: 0; padding: 0;
background-color: #f4f4f4; background-color: #f5f7fa;
color: var(--dark-color);
line-height: 1.6;
}
/* Container */
.container {
max-width: 1200px;
margin: 0 auto;
padding: 20px;
}
/* Navigation */
.nav {
display: flex;
justify-content: space-between;
align-items: center;
padding: 15px 20px;
background: linear-gradient(135deg, var(--primary-color), var(--secondary-color));
color: white;
box-shadow: var(--box-shadow);
border-radius: 0 0 var(--border-radius) var(--border-radius);
position: sticky;
top: 0;
z-index: 100;
}
.nav-list {
display: none;
list-style: none;
padding: 0;
margin: 0;
width: 100%;
background: white;
position: absolute;
top: 60px;
left: 0;
border-radius: var(--border-radius);
box-shadow: var(--box-shadow);
overflow: hidden;
}
.nav-list.active {
display: block;
}
.nav-list li {
padding: 12px 20px;
border-bottom: 1px solid #eee;
transition: all 0.3s ease;
list-style-type: none;
}
.nav-list li:last-child {
border-bottom: none;
}
/* Menüeinträge: Design wie der Logout-Button */
.nav-list li a {
color: var(--dark-color);
text-decoration: none;
font-weight: 500;
display: block;
padding: 8px 20px;
border-radius: var(--border-radius);
background: rgba(255, 255, 255, 0.2); /* Halbtransparenter Hintergrund */
transition: background-color 0.3s ease, transform 0.2s ease;
}
.nav-list li a:hover {
background-color: rgba(255, 255, 255, 0.3); /* Etwas dunklerer Hintergrund bei Hover */
transform: translateY(-2px); /* Leichtes Anheben beim Hover */
color: var(--dark-color); /* Textfarbe bleibt gleich */
}
/* Menüeinträge bei Hover: zusätzlicher Schatten */
.nav-list li:hover {
background-color: rgba(255, 255, 255, 0.3); /* Der Hintergrund ändert sich auch beim Hover auf den li */
box-shadow: 0 4px 8px rgba(0, 0, 0, 0.1); /* Dezent sichtbarer Schatten */
transform: translateY(-2px); /* Leichtes Anheben */
}
/* Hamburger Menu */
.hamburger {
display: block;
background: none;
border: none;
color: white;
font-size: 24px;
cursor: pointer;
padding: 5px;
}
.logout {
color: white;
text-decoration: none;
font-weight: 500;
padding: 8px 15px;
border-radius: var(--border-radius);
background: rgba(255, 255, 255, 0.2);
transition: var(--transition);
}
.logout:hover {
background: rgba(255, 255, 255, 0.3);
}
/* Tabelle */
table {
width: 100%;
border-collapse: separate;
border-spacing: 0;
margin: 20px 0;
background: white;
border-radius: var(--border-radius);
overflow: hidden;
box-shadow: var(--box-shadow);
}
th, td {
padding: 12px 15px;
text-align: left;
border-bottom: 1px solid #eee;
}
th {
background: var(--primary-color);
color: white;
font-weight: 600;
text-transform: uppercase;
font-size: 0.85em;
letter-spacing: 0.5px;
}
tr:last-child td {
border-bottom: none;
}
tr:hover {
background: #f8f9fa;
transition: var(--transition);
}
/* Button */
.btn-new {
display: inline-block;
background: var(--success-color);
color: white;
padding: 12px 20px;
text-align: center;
text-decoration: none;
border-radius: var(--border-radius);
font-weight: 600;
box-shadow: var(--box-shadow);
transition: var(--transition);
margin: 20px 0;
}
.btn-new:hover {
background: #3ab7d8;
transform: translateY(-2px);
box-shadow: 0 6px 12px rgba(0, 0, 0, 0.15);
} }
/* Cookie-Hinweis */ /* Cookie-Hinweis */
@ -12,11 +185,13 @@ body {
bottom: 0; bottom: 0;
left: 0; left: 0;
right: 0; right: 0;
background: #333; background: white;
color: #fff; color: var(--dark-color);
padding: 10px; padding: 15px;
text-align: center; text-align: center;
z-index: 1000; z-index: 1000;
box-shadow: 0 -2px 10px rgba(0, 0, 0, 0.1);
border-top: 1px solid #eee;
} }
/* Modal */ /* Modal */
@ -31,73 +206,52 @@ body {
bottom: 0; bottom: 0;
background: rgba(0, 0, 0, 0.5); background: rgba(0, 0, 0, 0.5);
z-index: 1001; z-index: 1001;
backdrop-filter: blur(3px);
} }
.modal-content { .modal-content {
background: #fff; background: white;
padding: 20px; padding: 30px;
border-radius: 5px; border-radius: var(--border-radius);
width: 90%; width: 90%;
max-width: 400px; max-width: 400px;
} box-shadow: var(--box-shadow);
transform: scale(1.05);
/* Navigation */ transition: var(--transition);
.nav {
display: flex;
justify-content: space-between;
align-items: center;
padding: 10px;
background: #333;
color: #fff;
}
.nav-list {
display: none;
list-style: none;
padding: 0;
margin: 0;
}
.nav-list li {
padding: 5px 0;
}
.hamburger {
display: block;
background: none;
border: none;
color: #fff;
font-size: 24px;
cursor: pointer;
}
.logout {
color: #fff;
text-decoration: none;
}
/* Tabelle */
table {
width: 100%;
border-collapse: collapse;
}
th, td {
padding: 8px;
text-align: left;
border-bottom: 1px solid #ddd;
}
/* Button */
.btn-new {
display: block;
background: #4CAF50;
color: white;
padding: 10px;
text-align: center;
text-decoration: none;
margin: 20px 0;
} }
/* Responsive */ /* Responsive */
@media (min-width: 768px) { @media (min-width: 768px) {
.nav-list { .nav-list {
display: flex; display: flex !important;
position: static;
background: transparent;
box-shadow: none;
border-radius: 0;
width: auto;
overflow: visible;
} }
.nav-list li {
padding: 0;
margin: 0 10px;
border-bottom: none;
}
.nav-list li a {
color: white;
padding: 5px 10px;
}
.nav-list li a:hover {
color: rgba(255, 255, 255, 0.8);
}
.nav-list li:hover {
background: var(--primary-hover);
transform: translateY(-3px);
}
.hamburger { .hamburger {
display: none; display: none;
} }

View file

@ -4,6 +4,6 @@ document.getElementById('accept-cookies').addEventListener('click', function() {
}); });
// Hamburger-Menü // Hamburger-Menü
document.querySelector('.hamburger').addEventListener('click', function() { // document.querySelector('.hamburger').addEventListener('click', function() {
document.querySelector('.nav-list').classList.toggle('show'); // document.querySelector('.nav-list').classList.toggle('show');
}); // });

View file

@ -1,9 +1,12 @@
<?php <?php
require 'config.php'; require 'config.php';
if (!isset($_SESSION['user_id'])) { // if (!isset($_SESSION['user_id'])) {
header('Location: index.php'); // header('Location: index.php');
exit; // exit;
} //}
// echo $_SESSION['user_id'];
error_log($_SESSION['user_id']);
// Login-Logik // Login-Logik
if ($_SERVER['REQUEST_METHOD'] === 'POST') { if ($_SERVER['REQUEST_METHOD'] === 'POST') {
@ -19,8 +22,8 @@ if ($_SERVER['REQUEST_METHOD'] === 'POST') {
} }
// Daten abrufen // Daten abrufen
$stmt = $pdo->prepare("SELECT * FROM entries WHERE user_id = ?"); $stmt = $pdo->prepare("SELECT * FROM entries");
$stmt->execute([$_SESSION['user_id']]); $stmt->execute();
$entries = $stmt->fetchAll(); $entries = $stmt->fetchAll();
?> ?>
<!DOCTYPE html> <!DOCTYPE html>

View file

@ -18,6 +18,7 @@ if (isset($_SESSION['user_id'])) {
<div id="cookie-notice" class="cookie-notice"> <div id="cookie-notice" class="cookie-notice">
<p>Diese Website verwendet nur technisch notwendige Cookies.</p> <p>Diese Website verwendet nur technisch notwendige Cookies.</p>
<button id="accept-cookies">OK</button> <button id="accept-cookies">OK</button>
<button class="hamburger">☰</button>
</div> </div>
<!-- Modal Login Dialog --> <!-- Modal Login Dialog -->

53
html/login.php Normal file
View file

@ -0,0 +1,53 @@
<?php
// login.php
require 'config.php';
// Verbindung herstellen
$conn = new mysqli($host, $user, $pass, $db);
// Verbindung prüfen
if ($conn->connect_error) {
die("Verbindung fehlgeschlagen: " . $conn->connect_error);
}
if ($_SERVER["REQUEST_METHOD"] == "POST") {
$input_username = $_POST['username'];
$input_password = $_POST['password'];
$sql = "SELECT id, username, password FROM users WHERE username = ?";
$stmt = $conn->prepare($sql);
$stmt->bind_param("s", $input_username);
$stmt->execute();
$result = $stmt->get_result();
if ($result->num_rows == 1) {
$row = $result->fetch_assoc();
if (password_verify($input_password, $row['password'])) {
echo "Login erfolgreich! Willkommen, " . htmlspecialchars($row['username']);
} else {
echo "Falsches Passwort!";
}
} else {
echo "Benutzer nicht gefunden!";
}
$stmt->close();
}
$conn->close();
?>
<!DOCTYPE html>
<html>
<head>
<title>Login</title>
</head>
<body>
<h2>Login</h2>
<form method="post" action="login.php">
Username: <input type="text" name="username" required><br>
Passwort: <input type="password" name="password" required><br>
<input type="submit" value="Login">
</form>
</body>
</html>

View file

@ -5,6 +5,43 @@ if (!isset($_SESSION['user_id'])) {
exit; exit;
} }
?> ?>
<?php
// save-Logik
if (!empty($_POST)) { // $_SERVER['REQUEST_METHOD'] === 'POST') {
echo "<h3>Empfangene POST-Daten:</h3>";
echo "<ul>";
// Durch alle POST-Variablen iterieren
foreach ($_POST as $key => $value) {
// Wert escapen, um XSS zu vermeiden
$escapedValue = htmlspecialchars($value, ENT_QUOTES, 'UTF-8');
echo "<li><strong>$key:</strong> $escapedValue</li>";
}
echo "</ul>";
// POST-Daten abrufen und escapen
$date = isset($_POST['date']) ? trim($_POST['date']) : '';
$user_id = isset($_POST['user_id']) ? trim($_POST['user_id']) : '';
$category = isset($_POST['category']) ? trim($_POST['category']) : '';
$subject = isset($_POST['subject']) ? trim($_POST['subject']) : '';
$amount = isset($_POST['amount']) ? (float)$_POST['amount'] : 0.0;
$payment_method = isset($_POST['payment_method']) ? trim($_POST['payment_method']) : '';
// SQL-Statement vorbereiten
$stmt = $pdo->prepare("
INSERT INTO entries (date, user_id, category, subject, amount, payment_method)
VALUES (:date, :user_id, :category, :subject, :amount, :payment_method)
");
$stmt->bindParam(':date', $date);
$stmt->bindParam(':user_id', $date);
$stmt->bindParam(':category', $category);
$stmt->bindParam(':subject', $subject);
$stmt->bindParam(':amount', $amount);
$stmt->bindParam(':payment_method', $payment_method);
// Statement ausführen
$stmt->execute();
}
?>
<!DOCTYPE html> <!DOCTYPE html>
<html lang="de"> <html lang="de">
<head> <head>
@ -16,8 +53,9 @@ if (!isset($_SESSION['user_id'])) {
<body> <body>
<div class="container"> <div class="container">
<h1>Neuer Eintrag</h1> <h1>Neuer Eintrag</h1>
<form action="dashboard.php" method="post"> <form action="new_entry.php" method="post">
<input type="date" name="date" required> <input type="date" name="date" required>
<input type="text" name="user_id" required>
<input type="text" name="category" placeholder="Kategorie"> <input type="text" name="category" placeholder="Kategorie">
<input type="text" name="subject" placeholder="Betreff" required> <input type="text" name="subject" placeholder="Betreff" required>
<input type="number" step="0.01" name="amount" placeholder="Betrag" required> <input type="number" step="0.01" name="amount" placeholder="Betrag" required>

47
html/register.php Normal file
View file

@ -0,0 +1,47 @@
<?php
// register.php
require 'config.php';
// Verbindung herstellen
$conn = new mysqli($host, $user, $pass, $db);
// Verbindung prüfen
if ($conn->connect_error) {
die("Verbindung fehlgeschlagen: " . $conn->connect_error);
}
if ($_SERVER["REQUEST_METHOD"] == "POST") {
$input_username = $_POST['username'];
$input_password = password_hash($_POST['password'], PASSWORD_DEFAULT);
$sql = "INSERT INTO users (username, password) VALUES (?, ?)";
$stmt = $conn->prepare($sql);
$stmt->bind_param("ss", $input_username, $input_password);
if ($stmt->execute()) {
echo "Registrierung erfolgreich!";
} else {
echo "Fehler: " . $sql . "<br>" . $conn->error;
}
$stmt->close();
}
$conn->close();
?>
<!DOCTYPE html>
<html>
<head>
<title>Registrierung</title>
</head>
<body>
<h2>Registrierung</h2>
<form method="post" action="register.php">
Username: <input type="text" name="username" required><br>
Passwort: <input type="password" name="password" required><br>
<input type="submit" value="Registrieren">
</form>
</body>
</html>

32
init.sql Normal file
View file

@ -0,0 +1,32 @@
-- Datenbank erstellen
CREATE DATABASE IF NOT EXISTS finanzapp;
USE finanzapp;
-- Benutzer "finanzapp" anlegen (falls nicht vorhanden)
CREATE USER IF NOT EXISTS 'finanzapp'@'%' IDENTIFIED BY 'finanzapp';
-- Alle Rechte auf die Datenbank finanzapp für den Benutzer finanzapp
GRANT ALL PRIVILEGES ON finanzapp.* TO 'finanzapp'@'%';
FLUSH PRIVILEGES;
-- Tabelle für Benutzer
CREATE TABLE IF NOT EXISTS users (
id INT AUTO_INCREMENT PRIMARY KEY,
username VARCHAR(50) NOT NULL UNIQUE,
password VARCHAR(255) NOT NULL
);
-- Tabelle für Einträge
CREATE TABLE IF NOT EXISTS entries (
id INT AUTO_INCREMENT PRIMARY KEY,
user_id INT NOT NULL,
date DATE NOT NULL,
category VARCHAR(50),
subject VARCHAR(255) NOT NULL,
amount DECIMAL(10,2) NOT NULL,
payment_method VARCHAR(50),
FOREIGN KEY (user_id) REFERENCES users(id)
);
-- Testbenutzer einfügen (Passwort: "test123")
INSERT INTO users (username, password) VALUES ('testuser', '$2y$10$92IXUNpkjO0rOQ5byMi.Ye4oKoEa3Ro9llC/.og/at2.uheWG/igi');