=== FW Real Estate ===
Contributors: fastw3b
Tags: real estate, property, listings, rentals, property search
Requires at least: 6.3
Tested up to: 7.1
Requires PHP: 8.1
Stable tag: 7.1.3
License: GPLv2 or later
License URI: https://www.gnu.org/licenses/gpl-2.0.html

Run a real property site on WordPress: listing pages, an advanced search, galleries, rentals, video and 3D tours. It's all in the download.

== Description ==

Your properties deserve better than a blog with photographs. FW Real Estate turns WordPress into a property site. You'll get a home page that presents your listings, list and grid listing pages, an advanced search a visitor can actually use, and detail pages with galleries and full specifications.

See it running: https://realestatewordpress.fastw3b.com/ (that demo has the full add-on range enabled, so it shows more than this plugin installs).

= Everything below is in the download =

There's nothing to buy first, no account needed, and nothing gets downloaded after you install it.

* **Properties on your own terms.** Your fields and your dictionaries: types, statuses, features, currencies.
* **Two listing layouts**, list and grid, both paged and both filterable.
* **A search that cascades** through country, region and city. Place it as a widget or as a block.
* **Detail pages that answer questions.** Photo gallery, specification tables, print view, quick view.
* **Rentals beside sales**, with their own lease terms, payment periods and pricing.
* **Video and 3D tours** on a property.
* **Shortcodes and native blocks**, so listings go on any page in any theme.
* **A WordPress admin**, with real roles and capabilities, and WP cron.

= Rentals, video and 3D tours are included =

A rental property carries its own lease terms, payment periods and pricing, so lettings sit beside sales without a second plugin. A property can hold a video. A 3D panorama tour opens in the gallery. All three are in this download.

= Put listings wherever you want them =

Add the listing shortcode to any page:

`[fw_real_estate layout="grid" limit="12"]`

and the detail shortcode (or `?fwre_view=item&fwre_id=ID`):

`[fw_real_estate type="item"]`

The native blocks are in the inserter too, so you never have to type a shortcode.

= Built on an engine that has been running for years =

Underneath is a real estate engine that has powered production property sites for years, integrated natively into WordPress. You aren't installing version 1 of anything, and it doesn't feel bolted on.

= It grows: MLS and IDX import, agent directories, and more =

When one site becomes an agency, add-ons take it there. Two of them lead the range:

* **MLS and IDX import.** Your listings arrive from the feed and stay in sync: the RESO Web API, and the UK and European portal feeds.
* **Agent directories.** Every agent gets a profile page with their own properties on it, and enquiries reach them.

The rest of the range covers maps, favourites, saved searches, comparison, status labels, an enquiry form, open houses, multi-currency, image watermarks and brochure PDFs. There's also a front-office manager, which lets agents post and edit properties without ever opening wp-admin.

Add-ons need a paid subscription and arrive as their own WordPress plugin, which you install like any other one. None of them is in this download, and this plugin never downloads code. The FAQ below explains exactly how that works.

== Installation ==

1. Upload the `fw-real-estate` folder to `/wp-content/plugins/`, or install the zip via Plugins → Add New.
2. Activate the plugin through the Plugins menu.
3. Create a page with the `[fw_real_estate]` shortcode for the listing, and one for the detail view.
4. Configure currency, display and other options under the FW Real Estate admin menu.

== External services ==

The plugin works without any of these. Each is inert until a site administrator turns it on or enters their own key, and none of them is contacted on a fresh install.

1. Fastw3b update and licence service — https://fastw3b.com
   What it is for: registering this site against a subscription and listing the add-ons it covers.
   When it is contacted: only from the plugin's own admin screens, on an administrator's action: connecting or verifying the site, and opening the Add-ons or Updates screen. Never from the front end, never on a schedule, and never on a fresh install before the administrator connects.
   What is sent: the site URL, the licence key, the plugin and WordPress versions, the platform name, and the list of FW Real Estate add-ons installed, so the service can answer which of them the subscription covers and whether newer versions exist. Nothing is downloaded from it: translations for this plugin come from translate.wordpress.org as WordPress language packs.
   Terms: https://fastw3b.com/terms · Privacy policy: https://fastw3b.com/privacy

2. Google reCAPTCHA — https://www.google.com/recaptcha
   What it is for: spam protection on the enquiry and review forms, if the administrator enables it and supplies a site key and secret. Off by default.
   When it is contacted: on any page that renders a protected form (the visitor's browser loads `api.js`), and on submission, when this site asks `api/siteverify` whether the answer was valid.
   What is sent: the visitor's reCAPTCHA token and this site's IP address.
   Terms: https://policies.google.com/terms — Privacy policy: https://policies.google.com/privacy

3. Map providers — Google Maps at https://maps.googleapis.com or Mapbox at https://api.mapbox.com
   What it is for: drawing the property map and geocoding an address. The administrator chooses the provider and supplies their own API key; with no key, no map is rendered and nothing is requested.
   When it is contacted: when a page showing a map is displayed in a visitor's browser. The provider's own map library is loaded from the provider, with that key, as both providers require.
   What is sent: the coordinates or address being displayed, and the administrator's API key.
   Google: https://cloud.google.com/maps-platform/terms and https://policies.google.com/privacy
   Mapbox: https://www.mapbox.com/legal/tos and https://www.mapbox.com/legal/privacy

4. YouTube and Vimeo — https://www.youtube.com and https://player.vimeo.com
   What it is for: playing a property video, when the property's own record names one.
   When it is contacted: only after the visitor clicks the video poster, which then embeds the player.
   What is sent: the video id, and whatever the embedded player itself collects.
   YouTube: https://www.youtube.com/t/terms and https://policies.google.com/privacy
   Vimeo: https://vimeo.com/terms and https://vimeo.com/privacy

== Frequently Asked Questions ==

= Is FW Real Estate free? =

Yes. The core is free and always has been, there's nothing to buy first, and you don't need an account to use it. It covers properties, fields, dictionaries and the whole front end on its own, and a great many sites never need more than that. What a paid subscription adds is add-ons.

= What are add-ons? =

Extensions that work only with FW Real Estate and add to what it can do. They come in three kinds: plugins for features such as maps, agents, favourites or rentals, designs for how the front end looks, and modules you can place on a page.

An add-on isn't a WordPress plugin of its own. You won't find it in the Plugins list, because it's managed inside FW Real Estate, on its own Add-ons screen. A paid pack, described below, is a WordPress plugin: it's the envelope the add-ons arrive in.

= Can I import listings from my MLS or IDX feed? =

Yes, with the MLS and IDX import add-on, which is paid. It reads the RESO Web API and the UK and European portal feeds, brings the listings into your site as properties, and keeps them in sync as the feed changes. It isn't in this download.

= Can each agent have their own page? =

Yes, with the Agents add-on, which is paid. Every agent gets a profile page carrying their own properties, and enquiries about those properties reach them. It isn't in this download either.

= How are add-ons installed? =

The free ones are already here. They ship inside this plugin, so there's nothing to install and nothing to download: open FW Real Estate → Add-ons and enable what you want.

Paid add-ons arrive as their own WordPress plugin, one per subscription tier, and you install it exactly like any other plugin (Plugins → Add New → Upload Plugin). Activating it hands its add-ons to FW Real Estate. Deactivating it takes them away again, which is what a lapsed subscription should look like.

This plugin never downloads or unpacks code. Plugins hosted here aren't allowed to, and FW Real Estate is built so that it can't.

= Why would I need an add-on? =

You might not. The core holds everything a property site can't work without, so it stands on its own. Every other feature is an add-on, which is how each site ends up carrying only what it actually uses.

That split is also why turning one off is clean. Disable an add-on and its fields, its output and its columns disappear from the site. Enable it again and they come back, with the data intact.

= How do I get a paid add-on? =

Take out or extend a subscription at https://fastw3b.com and download the pack it entitles you to, then install that pack as a WordPress plugin. Everything the site has received is listed under FW Real Estate → Add-ons, where each one can be enabled, disabled and updated.

= What does connecting the site to fastw3b.com do? =

It pairs this website with your fastw3b.com account. That's what makes support through the Client Section possible, and it lets the site be told when a new version of something it has is available.

One button does it: Connect, in the FW Real Estate admin header. Your client section opens, the site is registered, and the key comes back by itself. There's nothing to copy and no key to paste.

Connecting is optional. An unconnected site keeps working, and the free add-ons that ship inside this plugin work whether you connect or not.

== Screenshots ==

1. The search cascades through country, region and city, then narrows by category, type, beds, baths and price.
2. Property listings in a list: price, address, beds, baths and size, on any page you put the shortcode or the block.
3. The same listings as a photo grid. Both layouts are paged and both filter.
4. A property page opens on its photographs, with a counter, slide dots and a thumbnail strip, and carries the full specification underneath.
5. Quick view opens a property over the listing, so a visitor doesn't lose their place in the results.
6. Rentals sit beside sales, with their own leasing terms: deposit, payment period, minimum lease and the dates it is free.
7. A 3D tour plays where the photographs were, on its own tab.
8. A property can carry a video, played from its own record on the same tabs.
9. The property list in the WordPress admin: search, filter, group, publish.
10. Editing a property, with your own fields and dictionaries behind every selector.
11. The Add-ons screen: what's installed, what's enabled, and what the range adds.
12. The dictionaries every listing is built from: types, statuses, features and currencies, all yours to change.

== Changelog ==

= 7.1.3 =

**A small maintenance release.**

* **A backup made by an earlier version restores again.** Such a backup stores the files inside it with a leading slash, and the restore looked for them by exact name, so it answered that the archive was not a recognised backup and named the files it had just failed to find. This matters most if you are arriving from our previous product: export there, upload here, and the restore now reads it.
* **The dashboard tells you what the last update did**: when it ran, which version it installed, and what it changed in the database. Where an update cannot apply part of a database change, that is now recorded where you can read it rather than only in a server log, which much of shared hosting has switched off.
* **A comparison table and the spreadsheet importer show only your own fields.** Both could include a field that belongs to an add-on rather than to you, which meant a visitor could see it in a comparison and a spreadsheet column could write into it.
* **The date switches in the Fields list reach the property page.** Turning a date field on or off in the Fields list now shows and hides it on the property page as expected.
* **The enquiry e-mail lists only the details a property has**, and the default e-mail templates have been revised.
* **A restore that has nothing to add says so.** Restoring a previous-version backup into a site that already holds properties now reports that nothing was imported, and applies none of the backup's users, settings or media.
* **The property edit forms have been corrected.**
* **The search block lists every search field**, so each one can be shown or hidden from the block settings.

== Bundled third-party libraries ==

All of these ship inside the plugin and are loaded from it — the plugin never fetches code from a CDN. Each is GPL-compatible, and the readable upstream source sits beside the minified build it was made from, in the same directory:

* UIkit 3.25.21 (MIT) — https://getuikit.com — `assets/js/fw-uikit-3.25.21.min.js` + `fw-uikit-3.25.21.js`, `assets/js/fw-uikit-icons-3.25.21.min.js` + `fw-uikit-icons-3.25.21.js`, `assets/css/fw-uikit-3.25.21.min.css` + `fw-uikit-3.25.21.css`. This is the upstream 3.25.21 release with the CSS class prefix changed from `uk-` to `fwk-`, so the framework cannot collide with a theme or another plugin shipping stock UIkit. A custom prefix is a supported UIkit configuration and is documented by the project at https://getuikit.com/docs/avoiding-conflicts#custom-prefix — its own `pnpm prefix` script performs the same substitution over the published `dist`, and renames the global object the same way (`fwkUIkit`). The readable and the minified file are upstream's own pair with that one rename applied to both, so they are the same program; `scripts/vendor/build-fw-uikit.sh` in our repository regenerates all six files from the published upstream release.
* lightGallery 1.6.12 with the lg-zoom 1.1.0 and lg-fullscreen 1.1.0 modules (GPLv3) — https://github.com/sachinchoolur/lightGallery — `assets/js/lightgallery.min.js` + `lightgallery.js`, `lg-zoom.min.js` + `lg-zoom.js`, `lg-fullscreen.min.js` + `lg-fullscreen.js`, `assets/css/lightgallery.min.css` + `lightgallery.css`.
* Ion.RangeSlider 2.3.1 (MIT) — https://github.com/IonDen/ion.rangeSlider — `assets/js/ion.rangeSlider.min.js` + `ion.rangeSlider.js`, `assets/css/ion.rangeSlider.css`. 2.3.1 is the project's final release; it is no longer developed, so this is what its latest stable is.
* Pannellum 2.5.6 (MIT) — https://pannellum.org — `assets/js/pannellum.min.js`, with the upstream sources `pannellum.js` and `libpannellum.js` beside it and `assets/css/pannellum.min.css` + `pannellum.css`. Loaded from the plugin the first time a visitor opens a 3D tour.
* Pikaday (BSD & MIT, dual) — https://github.com/Pikaday/Pikaday — `assets/js/pikaday.js`, `assets/css/pikaday.css`. The date pickers on the availability and booking fields. Only the readable build ships; there is no minified copy to pair it with.
* Material Symbols Rounded (Apache-2.0) — https://fonts.google.com/icons — the icon outlines in `addons/designs/official/assets/js/demo-icons.js`. Not the font: the individual SVG paths for the icons this plugin's screens use, registered with the icon framework so a screen names an icon rather than embedding a drawing. No icon font is loaded and no request leaves the visitor's browser for one.
* MarkerClusterer for Google Maps 2.6.2 (Apache-2.0) — https://github.com/googlemaps/js-markerclusterer — `assets/js/markerclusterer.min.js` + `markerclusterer.js`. Both files are published by the project itself in that release: the minified one is its `dist/index.umd.js` and the readable one its `dist/index.dev.js`, the same program built without minification. Loaded only on a map that clusters pins.

Two typefaces ship as well, both under the SIL Open Font License 1.1 and both served from the plugin rather than from a font service — no request leaves the visitor's browser for a third party, and no visitor's IP address reaches one:

* Poppins (SIL OFL 1.1) — https://fonts.google.com/specimen/Poppins — `assets/fonts/fwre-poppins-{300,400,500,700}-{latin,latin-ext}.woff2`, eight files.
* Inter (SIL OFL 1.1) — https://fonts.google.com/specimen/Inter — `assets/fonts/fwre-inter-{cyrillic,greek}.woff2`, two files, carrying the Cyrillic and Greek that Poppins does not.

Both are the publisher's own woff2 subsets, redistributed unmodified; only the file names carry this plugin's prefix. Each `@font-face` declares a `unicode-range`, so a browser fetches only the files a page actually needs. The family names declared in CSS are prefixed too — `FWRE Poppins`, `FWRE Inter` — because font-family is a global name: an unprefixed one would MERGE with a theme's own declaration of the same family rather than override it or be overridden, and the browser would then pick between the two sets of files on its own.

`scripts/vendor/` in our repository regenerates every file above from the published upstream release, and each script records which release it fetched and how.

jQuery is NOT bundled: the plugin uses the copy that ships with WordPress.
