Feature: Kategoriefarben, Card Heights angepasst
All checks were successful
Docker Build & Push / build-and-push (push) Successful in 38s
All checks were successful
Docker Build & Push / build-and-push (push) Successful in 38s
This commit is contained in:
@@ -83,7 +83,7 @@ $types = str_repeat('i', count($household_member_ids));
|
||||
$sql = "SELECT
|
||||
a.id, a.name, a.weight_grams, a.quantity_owned, a.product_url, a.consumable, a.image_url, a.user_id, a.parent_article_id,
|
||||
u.username as creator_name, a.household_id, a.product_designation,
|
||||
c.id AS category_id, c.name AS category_name,
|
||||
c.id AS category_id, c.name AS category_name, c.color AS category_color,
|
||||
m.id AS manufacturer_id, m.name AS manufacturer_name,
|
||||
l2.name AS location_level2_name, l1.name AS location_level1_name
|
||||
FROM articles a
|
||||
@@ -399,15 +399,6 @@ document.addEventListener('DOMContentLoaded', function () {
|
||||
initializeInteractivity();
|
||||
}
|
||||
|
||||
function getColorForCategory(categoryName) {
|
||||
let hash = 0;
|
||||
for (let i = 0; i < categoryName.length; i++) {
|
||||
hash = categoryName.charCodeAt(i) + ((hash << 5) - hash);
|
||||
}
|
||||
const hue = Math.abs(hash % 360);
|
||||
return `hsl(${hue}, 60%, 85%)`;
|
||||
}
|
||||
|
||||
function generateCardHTML(article) {
|
||||
const imagePath = article.image_url ? article.image_url : 'assets/images/keinbild.png';
|
||||
const productLink = article.product_url ? `<a href="${article.product_url}" target="_blank" class="btn btn-sm btn-outline-secondary px-1 py-0" title="Produktseite öffnen"><i class="fas fa-external-link-alt"></i></a>` : '';
|
||||
@@ -427,7 +418,7 @@ document.addEventListener('DOMContentLoaded', function () {
|
||||
|
||||
const metaText = [article.manufacturer_name, article.product_designation].filter(Boolean).join(' - ');
|
||||
const catName = article.category_name || 'Ohne Kat.';
|
||||
const catColor = getColorForCategory(catName);
|
||||
const catColor = article.category_color || '#e2e8f0';
|
||||
|
||||
return `
|
||||
<div class="lager-card article-card" title="${article.name}${metaText ? ' (' + metaText + ')' : ''}">
|
||||
|
||||
@@ -116,7 +116,7 @@ elseif (isset($_GET['action']) && $_GET['action'] == 'delete' && isset($_GET['id
|
||||
$stmt_check->close();
|
||||
}
|
||||
|
||||
$categories_query = $conn->prepare("SELECT c.id, c.name, c.user_id, u.username as creator_name FROM categories c JOIN users u ON c.user_id = u.id WHERE c.user_id IN ($placeholders) ORDER BY c.name ASC");
|
||||
$categories_query = $conn->prepare("SELECT c.id, c.name, c.color, c.user_id, u.username as creator_name FROM categories c JOIN users u ON c.user_id = u.id WHERE c.user_id IN ($placeholders) ORDER BY c.name ASC");
|
||||
$categories_query->bind_param($types, ...$household_member_ids);
|
||||
$categories_query->execute();
|
||||
$categories_list = $categories_query->get_result()->fetch_all(MYSQLI_ASSOC);
|
||||
@@ -135,9 +135,13 @@ $conn->close();
|
||||
<div class="card-body">
|
||||
<h5 class="card-title mb-3">Neue Kategorie hinzufügen</h5>
|
||||
<form action="<?php echo htmlspecialchars($_SERVER["PHP_SELF"]); ?>" method="post" class="row g-3 align-items-end">
|
||||
<div class="col-sm-8">
|
||||
<label for="category_name" class="form-label visually-hidden">Neue Kategorie</label>
|
||||
<input type="text" class="form-control" id="category_name" name="category_name" placeholder="Name der neuen Kategorie" required>
|
||||
<div class="col-sm-6">
|
||||
<label for="category_name" class="form-label">Neue Kategorie</label>
|
||||
<input type="text" class="form-control" id="category_name" name="category_name" placeholder="Name" required>
|
||||
</div>
|
||||
<div class="col-sm-2">
|
||||
<label for="category_color" class="form-label">Farbe</label>
|
||||
<input type="color" class="form-control form-control-color w-100" id="category_color" name="category_color" value="#e2e8f0" title="Farbe wählen">
|
||||
</div>
|
||||
<div class="col-sm-4">
|
||||
<button type="submit" name="add_category" class="btn btn-primary w-100"><i class="fas fa-plus-circle me-2"></i>Hinzufügen</button>
|
||||
@@ -154,7 +158,7 @@ $conn->close();
|
||||
<?php foreach ($categories_list as $category): ?>
|
||||
<div class="list-group-item d-flex justify-content-between align-items-center">
|
||||
<div>
|
||||
<i class="fas fa-tag text-muted me-2"></i>
|
||||
<span class="badge border rounded-circle p-2 me-2" style="background-color: <?php echo htmlspecialchars($category['color'] ?? '#e2e8f0'); ?>; width:20px; height:20px; display:inline-block; vertical-align: middle;"></span>
|
||||
<span class="fw-bold"><?php echo htmlspecialchars($category['name']); ?></span>
|
||||
<?php if ($category['user_id'] != $current_user_id): ?>
|
||||
<small class="text-muted ms-2">(von <?php echo htmlspecialchars($category['creator_name']); ?>)</small>
|
||||
@@ -163,7 +167,7 @@ $conn->close();
|
||||
<?php if ($category['user_id'] == $current_user_id): ?>
|
||||
<div class="btn-group">
|
||||
<button type="button" class="btn btn-sm btn-outline-primary" title="Bearbeiten" data-bs-toggle="modal" data-bs-target="#editCategoryModal"
|
||||
data-id="<?php echo htmlspecialchars($category['id']); ?>" data-name="<?php echo htmlspecialchars($category['name']); ?>">
|
||||
data-id="<?php echo htmlspecialchars($category['id']); ?>" data-name="<?php echo htmlspecialchars($category['name']); ?>" data-color="<?php echo htmlspecialchars($category['color'] ?? '#e2e8f0'); ?>">
|
||||
<i class="fas fa-edit"></i>
|
||||
</button>
|
||||
<a href="categories.php?action=delete&id=<?php echo htmlspecialchars($category['id']); ?>" class="btn btn-sm btn-outline-danger" title="Löschen" onclick="return confirm('Sind Sie sicher, dass Sie diese Kategorie löschen möchten? Artikel, die dieser Kategorie zugewiesen sind, verlieren ihre Zuordnung.')">
|
||||
@@ -192,6 +196,10 @@ $conn->close();
|
||||
<label for="edit_category_name" class="form-label">Kategoriename</label>
|
||||
<input type="text" class="form-control" id="edit_category_name" name="category_name" required>
|
||||
</div>
|
||||
<div class="mb-3">
|
||||
<label for="edit_category_color" class="form-label">Farbe</label>
|
||||
<input type="color" class="form-control form-control-color w-100" id="edit_category_color" name="category_color" title="Farbe wählen">
|
||||
</div>
|
||||
</div>
|
||||
<div class="modal-footer">
|
||||
<button type="button" class="btn btn-secondary" data-bs-dismiss="modal">Abbrechen</button>
|
||||
@@ -210,10 +218,13 @@ document.addEventListener('DOMContentLoaded', function() {
|
||||
var button = event.relatedTarget;
|
||||
var id = button.getAttribute('data-id');
|
||||
var name = button.getAttribute('data-name');
|
||||
var color = button.getAttribute('data-color');
|
||||
var modalIdInput = editModal.querySelector('#edit_category_id');
|
||||
var modalNameInput = editModal.querySelector('#edit_category_name');
|
||||
var modalColorInput = editModal.querySelector('#edit_category_color');
|
||||
if (modalIdInput) modalIdInput.value = id;
|
||||
if (modalNameInput) modalNameInput.value = name;
|
||||
if (modalColorInput) modalColorInput.value = color;
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
@@ -56,4 +56,10 @@ if ($check_todo_list_id && $check_todo_list_id->num_rows == 0) {
|
||||
$conn->query("ALTER TABLE packing_lists ADD COLUMN todo_list_id INT DEFAULT NULL");
|
||||
$conn->query("ALTER TABLE packing_lists ADD CONSTRAINT fk_packing_list_todo FOREIGN KEY (todo_list_id) REFERENCES todo_lists(id) ON DELETE SET NULL");
|
||||
}
|
||||
|
||||
// Ensure color exists in categories
|
||||
$check_category_color = $conn->query("SHOW COLUMNS FROM categories LIKE 'color'");
|
||||
if ($check_category_color && $check_category_color->num_rows == 0) {
|
||||
$conn->query("ALTER TABLE categories ADD COLUMN color VARCHAR(7) DEFAULT '#e2e8f0'");
|
||||
}
|
||||
?>
|
||||
|
||||
@@ -159,7 +159,7 @@ $conn->close();
|
||||
border: 1px solid #eee; border-radius: 8px; padding: 6px;
|
||||
text-align: center; background: #fff; display: flex; flex-direction: column;
|
||||
transition: transform 0.1s, box-shadow 0.1s;
|
||||
height: 200px;
|
||||
height: 205px;
|
||||
}
|
||||
.lager-card:hover { transform: translateY(-2px); box-shadow: 0 4px 8px rgba(0,0,0,0.05); }
|
||||
.lager-img-wrapper {
|
||||
|
||||
@@ -107,6 +107,7 @@ $sql = "SELECT
|
||||
COALESCE(a.weight_grams, bp.weight_grams, 0) as weight_grams,
|
||||
a.image_url, a.product_designation, a.consumable,
|
||||
COALESCE(c.name, c_bp.name, 'Sonstiges') AS category_name,
|
||||
COALESCE(c.color, c_bp.color, '#e2e8f0') AS category_color,
|
||||
m.name AS manufacturer_name,
|
||||
COALESCE(NULLIF(u.display_name, ''), u.username) AS carrier_name,
|
||||
u.id AS carrier_id
|
||||
@@ -272,7 +273,14 @@ function render_item_row($item, $level, $items_by_parent) {
|
||||
echo '<td class="text-center">' . ($item['consumable'] ? '<i class="fas fa-cookie-bite text-warning" title="Verbrauch"></i>' : '') . '</td>';
|
||||
echo '<td>' . htmlspecialchars($item['manufacturer_name'] ?: '') . '</td>';
|
||||
echo '<td>' . htmlspecialchars($item['product_designation'] ?: '') . '</td>';
|
||||
echo '<td>' . htmlspecialchars($item['category_name'] ?: '') . '</td>';
|
||||
|
||||
echo '<td>';
|
||||
if ($item['category_name'] !== 'Sonstiges' && !empty($item['category_name'])) {
|
||||
echo '<span class="badge rounded-pill" style="background-color: ' . htmlspecialchars($item['category_color']) . '; color: #333; font-weight: 500;">' . htmlspecialchars($item['category_name']) . '</span>';
|
||||
} else {
|
||||
echo '<span class="text-muted">---</span>';
|
||||
}
|
||||
echo '</td>';
|
||||
|
||||
echo '<td class="text-center">';
|
||||
if ($is_backpack) {
|
||||
|
||||
Reference in New Issue
Block a user