#110 — Einkaufsliste — UI-Kleinigkeiten (Menü-Sichtbarkeit, Mengen-Anzeige, Online-Warenkorb) #113
Labels
No labels
priority/could
priority/must
priority/should
priority/wont
status/blocked
status/claimed
status/done-migrated
type/bug
type/feature
type/infra
type/tech-debt
No milestone
No project
No assignees
1 participant
Notifications
Due date
No due date set.
Dependencies
No dependencies set
Reference
robert/todo#113
Loading…
Reference in a new issue
No description provided.
Delete branch "%!s()"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Story: Einkaufsliste — UI-Kleinigkeiten (Menü-Sichtbarkeit, Mengen-Anzeige, Online-Warenkorb)
As a Nutzer der Einkaufsliste,
I want to ein paar kleinere Inkonsistenzen zwischen Einkaufsliste und Todo-Liste behoben haben,
so that sich beide Listentypen gleich bedienen lassen.
Vier unabhängige, jeweils kleine Punkte, gebündelt in einer Story:
1. "..."-Menü in der Listen-Übersicht immer sichtbar
ShoppingListItem.tsxs Menü-Button nutztopacity-0 group-hover:opacity-100,ListActionsMenu.tsx(Todo-Pendant) nutztopacity-50 group-hover:opacity-100— die Einkaufsliste istalso unsichtbar statt nur abgeblendet ohne Hover.
ShoppingListItem.tsxs Menü-Button auf dasselbeopacity-50-Verhalten wieListActionsMenu.tsxumstellen.
2. Mengen-Anzeige: Präfix statt Suffix, normale statt größerer Schrift
"5 Dosen Kokosmilch" statt "Dosen Kokosmilch 5"), in derselben Schriftgröße wie der Produktname.
3. Online-Warenkorb — Rückweg
ShoppingCartCheckPanelist kein eigener Screen/eine eigene Route, sondern eineinblendbares Panel innerhalb von
ShoppingListPage.tsxmit einem funktionierenden ✕-Schließen-Button(
onClose); die normale Produktliste bleibt technisch die ganze Zeit im DOM. Der gemeldete "kein Wegzurück"-Eindruck deutet auf ein Auffindbarkeits-/Layout-Problem hin (z. B. auf kleinen Viewports der
Schließen-Button außerhalb des sichtbaren Bereichs), nicht auf eine fehlende Funktion.
mobil) sichtbar und erreichbar sein, ohne zu scrollen oder zu suchen.
4. Online-Warenkorb — Sammel-Löschen abgehakter Punkte
IsInCart = true) Punkteauf einmal von der Einkaufsliste entfernen können, so that ich nach dem Abschicken einer
Online-Bestellung nicht jeden Punkt einzeln abhaken/löschen muss.
Abhaken-Verhalten je nach Ausgang von Story
#109) alle Produkte mitIsInCart = truein einem Schritt.Lösch-Bestätigungen in dieser Codebase).
Out of scope for this story:
#103–#109behandelt wird.design (
110_shopping_ui_polish_bundle_design.md)Design note —
#110Einkaufsliste UI-KleinigkeitenFour independent frontend-only fixes, no backend/DB changes and no new commands — every mutation
path already exists.
1. "..."-Menü immer sichtbar
ShoppingListItem.tsx's menu button switches fromopacity-0 group-hover:opacity-100toopacity-50 group-hover:opacity-100, matchingListActionsMenu.tsx's Todo-list equivalentverbatim.
2. Mengen-Anzeige als Präfix
ShoppingQuantityis a free-text field (e.g."5 Dosen"), not a number — the AC's example ("5Dosen Kokosmilch") is just quantity-text-then-name concatenation with a space, no new formatting
logic needed. Two render sites show quantity next to a product name:
ShoppingProductItem.tsx(the main list row)RecentlyCheckedOffPanel.tsx(the restore-history panel)Both move the
{product.quantity}span before the name span and drop thetext-xssize class (soit inherits the row's
text-sm, same as the name) — color (text-muted-foreground) is unchanged,only prefix/suffix order and size were in scope per the AC.
ShoppingCartCheckPanel.tsxintentionally shows name only (no quantity) — pre-existing, unrelatedto this story, and covered by its own test (
'name only (no quantity/comments)').3. Online-Warenkorb — Rückweg immer erreichbar
Root cause confirmed:
ShoppingCartCheckPanel's outerdivappliedmax-h-64 overflow-y-autotoboth the header (title + ✕) and the product list together. With enough products, scrolling the
list scrolls the header off-screen — no separate route, no missing handler, just a layout bug that
makes a working close button unreachable without scrolling back up first (exactly the reported
symptom).
Fixed by splitting into a fixed header (
shrink-0, never scrolls) and a separately-scrollable body— the same structure
RecentlyCheckedOffPanel.tsxalready uses correctly one file over. Verifiedat mobile width (375px) in the local dev server: header with ✕ stays pinned regardless of list
length or scroll position.
4. Sammel-Löschen abgehakter Online-Warenkorb-Punkte
No new backend command:
DeactivateShoppingProductCommandalready clearsIsOnList,IsInCart,and
InCartSourcein one call — exactly what "remove from list" needs per product, and it's thesame command the individual checkbox/quantity-dialog paths already use. Bulk removal composes it
in a sequential loop from the frontend, the same "compose existing single-item commands" tradeoff
already established for CSV import (
#83) rather than adding a new batch endpoint for a low-volume,owner-only-triggered action.
New
ShoppingCartCheckPanelproponRemoveInCartItems: (products: ShoppingProductDto[]) => Promise<void>.ShoppingListPageimplements it: loopdeactivateShoppingProduct+patchProduct+pushShoppingCheckedOffper item — literallyhandleCheck's existing body (renamed fromhandleUncheckby#109, which landed mid-cycle and was merged into this branch before this storywas implemented), called once per in-cart product, so removed items land in "Recently checked off"
exactly like a normal manual check-off. Matches the AC's "analog zum normalen
Abhaken-Verhalten" against
#109's now-delivered semantics (checking a box off removes the item fromthe active list).
Button only renders when at least one visible product has
isInCart; a confirm dialog (samepattern as every other destructive action in this codebase —
ShoppingListItem's delete dialog,ShoppingProductItem's delete dialog) gates the actual removal. Products not in the cart areuntouched (the loop only ever iterates the filtered in-cart subset).