loyality-qr-wallet is a loyalty QR wallet product built for the business side: a business runs its own loyalty program for its own customers. The business owner sets up a program, issues loyalty QR codes, and tracks customer participation and rewards; their customers scan those QR codes at the point of interaction to collect stamps/points, hold their loyalty cards and rewards in a wallet, and redeem accumulated rewards.
The product intent is a small gift economy made operational: the register-side work is real and durable, but the experience must feel pleasant, optimistic and almost toy-like — scanning a QR code should feel like a small reward in itself, never like enterprise admin. The audience is everyday shop owners and everyday shoppers: coffee shops, salons, bakeries, gyms, retail.
The audience for this document is the implementing team (design, frontend, backend) and the product owner.
loyality-qr-wallet is a custom-UI web application with an application-owned backend. It has two accepted human actors:
Current delivery is a first-party application with application-owned identity: both actors establish identity on first use and verify it on return, because each holds durable, actor-specific state (the business owner's program, QR codes and participation records; the customer's cards, stamp balances and rewards). The anonymous entry surface (Landing) explains the product before any identity is established.
Narrow exclusions. The product is for the business side, not for shoppers to run their own program. Shoppers are loyalty members of a business's program; they do not create or operate programs of their own. No adjacent capabilities beyond the accepted loyalty lifecycle are in scope.
Delivery ownership. All accepted behavior is delivered by the first-party application: the business owner's program operation and the customer's wallet, scanning and redemption are custom application surfaces backed by the application's own backend and durable storage. There is no provider-owned or external-only surface in the accepted scope, and no headless-only delivery.
Access ownership. Identity is application-owned. The Landing surface is anonymously reachable and establishes no identity. Business Login and Customer Login are the anonymous entry boundaries where each actor establishes identity on first use and verifies it on return; they are reachable without an existing session because a protected destination cannot own the interaction that establishes access to itself. Dashboard, Program Setup and QR Codes are restricted to the business owner; Wallet, Scan and Redeem are restricted to the customer. Access restriction here is actor-continuity restriction — each actor's durable state must remain bound to the correct participant — not a differentiated permission model over shared product state.
Current vs. future. Everything described in this document is current. No future-horizon requirements were accepted.
Not applicable — no reference directive declares content_source.
prefers-reduced-motion, the blob drift stops and the bottom ticker resolves into a static two-row list.prefers-reduced-motion, the stack becomes a static vertical list.FR-1 — Business owner first-use enrollment and returning verification (required_inference) As a Business Owner / Loyalty Program Operator, I should be able to establish my identity on first use and verify it on return, so that my program and its durable records stay bound to me.
FR-2 — Customer first-use enrollment and returning verification (required_inference) As a Customer / Loyalty Member, I should be able to establish my identity on first use and verify it on return, so that my cards, stamp/point balances and rewards stay bound to me.
FR-3 — Business owner sets up its own loyalty program (explicit) As a Business Owner / Loyalty Program Operator, I should be able to set up my own loyalty program for my customers, so that my business has a program to run.
FR-4 — Business owner operates its loyalty program (explicit) As a Business Owner / Loyalty Program Operator, I should be able to operate my own loyalty program for my customers, so that the program keeps running as I intend.
FR-5 — Business owner issues loyalty QR codes (explicit) As a Business Owner / Loyalty Program Operator, I should be able to issue loyalty QR codes, so that my customers have a code to scan to collect stamps/points.
FR-6 — Business owner manages loyalty QR codes (explicit) As a Business Owner / Loyalty Program Operator, I should be able to manage the loyalty QR codes I have issued, so that the codes in circulation match what my program needs.
FR-7 — Business owner tracks customer participation and rewards (explicit) As a Business Owner / Loyalty Program Operator, I should be able to track customer participation and rewards, so that I can see how my customers are engaging and keep them returning.
FR-8 — Customer scans a business's loyalty QR code to collect stamps/points (explicit) As a Customer / Loyalty Member, I should be able to scan a business's loyalty QR code to collect stamps/points, so that my visits accumulate toward a reward.
FR-9 — Customer holds and views loyalty cards and rewards in a wallet (explicit) As a Customer / Loyalty Member, I should be able to hold and view my loyalty cards and rewards in a wallet, so that everything I have collected is in one place.
FR-10 — Customer redeems accumulated loyalty rewards (explicit) As a Customer / Loyalty Member, I should be able to redeem accumulated loyalty rewards, so that my collected stamps/points turn into something I actually get.
FR-11 — Anonymous product entry (required_inference) As a visitor (Business Owner / Loyalty Program Operator or Customer / Loyalty Member), I should be able to understand what the loyalty QR wallet product is, who it is for, and what it does before establishing any identity, so that I can choose the right entry.
FR-12 — Program prerequisite for scanning (required_inference) As a Business Owner / Loyalty Program Operator, I should have set up a loyalty program and issued a QR code before a customer can scan and collect stamps/points, so that a scan always resolves to a real program.
FR-13 — Reward eligibility prerequisite (required_inference) As a Customer / Loyalty Member, I should have collected enough stamps/points before redeeming a reward, so that redemption reflects what I actually earned.
Product context. This is the business side of the product. The owner runs a small everyday business — a coffee shop, salon, bakery, gym or retail store — and runs its own loyalty program for its own customers. They are not administering someone else's platform; the program, its codes and its records are theirs.
Primary goal. Keep customers returning by running a loyalty program that is easy to operate at the counter and that shows them how their customers are engaging.
Distinct accepted responsibilities. Setting up the program and defining its settings; operating the program by editing and saving those settings; issuing loyalty QR codes bound to the program; managing the codes already issued; and tracking customer participation and rewards.
Relevant inputs and decisions. The program's settings and reward definition; when to issue a code and which code to display at the point of interaction; how to read participation and reward activity and what to change in response.
Interactions with other accepted participants. The owner's issued QR code is the object the Customer / Loyalty Member scans. The owner's program is what the customer's stamps/points and rewards accrue against. The owner sees the participation and reward activity that the customer's scans and redemptions produce.
Observable success. The program exists and is configured as intended; a QR code is issued and displayable; participation and reward activity are visible on Dashboard; customers keep collecting and redeeming.
Constraints. The product is for the business side, not for shoppers to run their own program. This role is the one that owns and operates the program.
Product context. This is the shopper side of the product. The customer is an everyday shopper at a business whose loyalty program they have joined. They interact with the product at the point of interaction — at the counter, on a phone — and they hold their loyalty cards and rewards in a wallet.
Primary goal. Collect stamps/points on their visits and turn them into rewards, without friction and without having to think about admin.
Distinct accepted responsibilities. Scanning a business's loyalty QR code to collect stamps/points; holding and viewing their loyalty cards and rewards in a wallet; and redeeming accumulated rewards once enough stamps/points have been collected.
Relevant inputs and decisions. The QR code presented by the business at the point of interaction; which card in the wallet to look at; which available reward to redeem and when.
Interactions with other accepted participants. The customer scans the QR code the Business Owner / Loyalty Program Operator issued. Their stamps/points and rewards accrue against that owner's program, and their scans and redemptions are what the owner sees as participation and reward activity.
Observable success. A scan collects a stamp/point and the progress row advances; the wallet shows the cards, progress and rewards; a reward is redeemed and the balance updates.
Constraints. The customer is a loyalty member of a business's program; they do not create or operate a program of their own.
Muse and headline. Karim Rashid — sensual pop minimalism for the loyalty counter: glossy candy curves on a hot pink field. Loyalty is a small gift economy; glossy, organic, candy-coloured forms make a stamp feel like a prize. The business side gets a program builder that looks like a design object instead of a neutral dashboard; the customer side gets a wallet that feels like a bright plastic card holder. The "for the business side" constraint is a role boundary, not a mandate for grey UI.
Colour tokens (light mode).
| Role | Hex | Use |
|---|---|---|
| Background | #FFF4F7 | Warm bubblegum white ground — never a neutral grey |
| Surface | #FFFFFF | Glossy white cards and capsules |
| Text (ink) | #1B1024 | Deep plum ink; sits warmly on pink rather than reading as black |
| Primary | #FF2E88 | Hot pink — large colour fields, buttons, active states, QR frame |
| Accent | #B9FF3D | Acid lime — reward-ready moments, stamp bursts, the "collected" tick only |
| Muted | #7A6A82 | Secondary labels |
Ratio: 60% pink/white ground, 25% white glossy surface, 10% ink, 5% lime. Contrast: ink on #FFF4F7 and white on #FF2E88 both pass body-size contrast. Never set body copy in lime, and never pink on pink.
Typography.
Shape language. Organic and glossy. Everything is a capsule, a blob or a soft-squircle: cards at 28–36px radii, buttons fully pill (999px), stamp tokens as perfect circles with a thin inner ring. Section boundaries are gentle curves — a wide elliptical pink arc that dips into the next section. Controls look moulded, not drawn: a 2px inner highlight along the top edge of a button reads as a glossy plastic catch-light. No hard 90-degree corners anywhere except the QR code modules themselves, which stay square to remain scannable.
Layout. Mobile-first, one dominant column on phones; asymmetric two-column on desktop with a 12-column grid and a consistent 24px gutter. Business pages (Dashboard, Program Setup, QR Codes) use a left rail of pill-shaped tabs and a canvas of stacked glossy cards with big numerals. Customer pages (Wallet, Scan, Redeem) use a centred card-stack metaphor — the active loyalty card sits slightly rotated above two ghost cards behind it. Never a grid of identical hover-lift cards: cards differ by size and by the colour field they sit on. Generous 32–64px breathing room around every cluster.
Imagery. Glossy 3D candy objects rendered as abstract stand-ins for loyalty: a pink torus of stamps, a lime capsule counter, a chrome QR plaque, floating soap-bubble spheres. No stock photography of people, no clip art. On the customer side, one photographed or rendered macro of a phone held at a counter, cropped so the phone bleeds off the right edge. Icons are rounded, 2px-stroke, filled with candy colour, never outlined-only.
Readable-text rule. Headlines, wordmarks, labels, numbers, card text and controls stay entirely inside the viewport and their container at 375px, 768px and 1280px, wrapping or scaling (for example font-size: clamp(...) with its mobile size) to fit, and no other element covers any part of them. Imagery, decoration and motion may be cropped, bled off an edge, rotated, overlapped or cut exactly as the direction asks, as long as they cover no readable text or control. Moving and scrollable content may cross the viewport or container edge by design; every item must become fully readable as it passes.
The hero object is the loyalty card, not an illustration.
The public entry (Landing) is a full-bleed bubblegum field (#FFF4F7) with a giant flat hot-pink organic blob (#FF2E88, one soft inner shadow, no gradient) occupying the right 55% of the viewport and bleeding off the top and right edges. Overlapping the blob's left curve sits a glossy white capsule card — the loyalty card — rotated −4°, carrying a pink QR plaque and a row of eight stamp circles with the first five filled lime. The headline is set in Comfortaa 700 at 44px on mobile to 112px on desktop, stacked in three short lines flush-left in the upper left, with the words "stamps" and "rewards" set in lime against the pink blob so they punch. Below the headline, a single pill CTA "Start your program" in ink-on-lime, and a secondary text link "I have a card". A thin marquee of tiny stamp tokens drifts left-to-right along the bottom edge, crossing the viewport edge by design. A wide elliptical pink arc dips into the next section instead of a straight divider, so the page reads as one continuous moulded surface.
No centred headline, no sub-headline paragraph, no blue button, no gradient blob: the blob is flat colour with one soft inner shadow, and the QR plaque is the only square thing on the screen.
This concept recomposes only accepted content and controls — the product explanation, the two entry routes, the loyalty card, the stamp row and the QR plaque. It introduces no new behaviour, page or destination.
Interaction Model: Animated Motion Tempo: expressive Hero Dimensionality: layered_2d
Landing Hero Motion Brief
prefers-reduced-motion is set.durable_state_required; rationale: the accepted lifecycles create and change durable relationships and value.)app_owned_identity; rationale: both accepted actors hold durable, actor-specific state.)prefers-reduced-motion, the hero blob drift stops, the ticker resolves into a static two-row list, and the wallet card stack becomes a static vertical list. No decorative motion runs. (Source: creative direction.)#FFF4F7 and white on #FF2E88 must pass body-size contrast; body copy is never set in lime, and never pink on pink. (Source: creative direction.)requires_backend_integration.)docker-compose.yml as the inventory of runnable services; the backend and its storage run as the project's services. Kubernetes is not required by any accepted requirement.[Default — not specified by user] for the concrete storage engine and container orchestration details; the source specifies no technology choices beyond the product's functional shape.
Constraints
Assumptions
No completed page designs yet.
Completed design pages will appear here when they are ready to preview.
No completed page designs yet.
Completed design pages will appear here when they are ready to preview.
No comments yet. Be the first!