Housing development site
A sales site for a 142-flat development, built around what the price-transparency act asks of a developer: every flat on a stacking plan, every price with its history, a public price feed. The client and the estate are fictional — the site and its code are real.
- Client
- Lenno Development — a fictional client, webmotion demo project
- Industry
- Residential property development
- Timeline
- September–October 2026
- Services
- Design, Development, Maintenance, Performance, Security
- Team
- One — Figma design and WordPress build
- Live at
- lenno.webmotion.io
What the project had to solve
The problem as it stood, and the decision that answered it.
A price list buyers can trust, not a brochure with a PDF attached
Since the act of 21 May 2025 on housing price transparency, a developer has to publish the price of every unit, its history and the ancillary costs, and keep them in a machine-readable form. Most developer sites bolt a PDF price list onto a brochure. Here the price list had to be the site.
- 142 flats, with status and price on every view
- A full price history per flat and a public feed
- Polish and English without keeping two price lists
One price list, and every view reads from it
Flats are a single post type holding the price, its history and the status. The search, the unit pages, the PDF cards, the clipboard and the public feed all read the same records, and one CSV import from the sales team updates every one of them.
- Flats are not translated — one record serves both languages
- A price change appends to the history automatically
- Live availability counts inside editable text
The stack we built it on
The same benchmark every webmotion project starts from, plus the few pieces a developer's price list needed.
- WordPress CMS and block editor
- ACF Pro 24 custom blocks and the unit fields
- Polylang PL / EN across pages, posts and options
- PHP 8.2+ Typed services for prices and units
- Sage 11 Roots theme scaffolding
- Acorn 6 Laravel container inside WordPress
- Blade Views, composers, services
- Alpine.js Search and clipboard over one JSON of all flats
- Tailwind CSS v4 Tokens taken from the Figma style board
- Geist Self-hosted, Latin Extended
- Lenis Smooth scrolling and anchor glides
- PhotoSwipe 5 Gallery lightbox
- Vite 6 Asset build and HMR
- ddev / Docker Identical local environments
- GitLab CI + Deployer Tests, then deploy
- LiteSpeed + LSCache Production server and page cache
What we connected it to
Each card names the system, what it does on this site, and which way the data moves.
-
CSV / XML
Public price feed
The full price list at /ceny.csv and /ceny.xml, with history and ancillary costs, plus a daily 06:00 snapshot ready for dane.gov.pl.
Site → buyers, dane.gov.pl -
Import
Price import
The sales team uploads a spreadsheet in the admin or through WP-CLI; prices and statuses change everywhere and the history grows by itself.
Spreadsheet → site -
PDF
dompdf
Every flat has a PDF card generated on request, with the plan, parameters and price, in either language.
Unit → PDF -
Forms
Contact Form 7
Three forms templated in Blade: a unit inquiry, a meeting booking with a calendar, and the clipboard sent to an advisor.
Visitor → advisor -
i18n
Polylang + ACF Options
Pages, buildings, the construction log and the team are translated; flats stay one record with English URLs added by a rewrite rule.
PL ⇄ EN -
Maps
OpenStreetMap
Location maps rendered from OSM data and recoloured to the brand palette, with the OpenStreetMap credit kept on the page.
OSM → static map
Colours and type it ships with
The client's palette, applied as tokens — every swatch below is a variable the theme exports.
- Navy #102C57 Text, accents, dark sections, available
- Cream #FEFAF6 Page
- Beige #EADBC8 Panels, cards, section grounds
- Tan #DAC0A3 Borders and rules
- Bronze #8A6A45 Reserved status
- Taupe #6F675E Sold status
- Regular 400
- Medium 500
- SemiBold 600
- Display
- 88 / 0.98 / −0.04em
- Section heading
- 44 / 1.08 / −0.03em
- 689 900 zł
- 28 / 1.2 / 600
- Body copy sets at seventeen over 1.6
- 17 / 1.6 / 400
- Eyebrow label
- 13 / 0.08em / upper
- 6px Buttons, inputs
- 12px Cards, panels
- 999px Status badges, chips
The product itself
Captured from the live site. Every tile opens in a lightbox at full size.
What we actually built
The six pieces the site stands on — the ones a developer's sales team actually uses.
-
01
A stacking plan, not a filter form
Every flat is a square coloured by its status. Filtering runs in the browser over one JSON of all 142 flats, so it is instant and still works behind the page cache.
-
02
Price history by design
Changing a price appends the old one to the history. Each unit page shows it as a chart and a table, with the ancillary costs underneath.
-
03
A public price feed
/ceny.csv and /ceny.xml serve the whole price list, and a daily snapshot is written to the uploads for publication on dane.gov.pl.
-
04
One import updates the site
A CSV from the sales team changes prices and statuses on the search, the unit pages, the PDFs and the feed at once.
-
05
Saved flats without an account
The clipboard lives in the browser, compares up to three flats and sends the list to an advisor through a form.
-
06
Live counts in editable text
Editors write {available} or {sold} in a heading and the number comes from the price list, so no page claims flats that are gone.
What it changed
Measured on the live site rather than estimated — the note under each figure says where it came from.
What the developer's sales team can run without opening the codebase.
- Ten views designed in Figma for desktop and mobile
- 24 ACF blocks and five custom post types
- Stacking-plan search, unit pages and the clipboard
- Price history, CSV/XML feed and CSV import
- PDF unit cards and buyer documents
- Polish and English, down to the forms and options
Have a project that should work like this one?
Send the brief, or book a call and talk it through. We answer with scope and a range, not a template.