react-listing-engine 0.7.3 → 0.7.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +15 -0
- package/dist/chunk-CJQJDGBU.js +2 -0
- package/dist/chunk-HTNCZ5NS.cjs +2 -0
- package/dist/index.cjs +1 -1
- package/dist/index.d.cts +28 -4
- package/dist/index.d.ts +28 -4
- package/dist/index.js +1 -1
- package/dist/{listing-app-C7EeHlmP.d.cts → listing-app-BKE75k--.d.cts} +60 -8
- package/dist/{listing-app-DHFJtnKI.d.ts → listing-app-CRGXBErM.d.ts} +60 -8
- package/dist/styled/index.cjs +1 -1
- package/dist/styled/index.d.cts +2 -2
- package/dist/styled/index.d.ts +2 -2
- package/dist/styled/index.js +1 -1
- package/dist/styles.css +31 -0
- package/package.json +1 -1
- package/dist/chunk-TX6KIOD7.js +0 -2
- package/dist/chunk-X4LBPNOS.cjs +0 -2
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,20 @@
|
|
|
1
1
|
# react-listing-engine
|
|
2
2
|
|
|
3
|
+
## 0.7.5
|
|
4
|
+
|
|
5
|
+
### Patch Changes
|
|
6
|
+
|
|
7
|
+
- Add a `mobileSheetFooter` render-prop to `ListingApp` so consumers can own the mobile filters bottom-sheet footer. It receives `{ draft, apply, clear, resultCount, loading }` (exported as `MobileSheetFooterContext`), letting the consumer render a LIVE preview count for the deferred draft (e.g. via its own count endpoint) instead of the default applied count. When the prop is omitted, the default footer (Clear all + "Show N results") is unchanged.
|
|
8
|
+
|
|
9
|
+
## 0.7.4
|
|
10
|
+
|
|
11
|
+
### Patch Changes
|
|
12
|
+
|
|
13
|
+
- Mobile filters bottom-sheet improvements:
|
|
14
|
+
|
|
15
|
+
- The sheet's "Show N results" apply button now shows a loading spinner (and is disabled) while a filter refetch is in flight.
|
|
16
|
+
- The sheet now **defers** filter application: changing a control buffers into a draft instead of applying live, and only the "Show results" button commits the draft to the engine (the list + map update then, and the sheet closes once the refetch settles). `ListingFilters` gains optional `draft` / `onDraftChange` props to drive this deferred mode; the desktop filter bar is unchanged (still applies live).
|
|
17
|
+
|
|
3
18
|
## 0.7.3
|
|
4
19
|
|
|
5
20
|
### Patch Changes
|
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
"use client";
|
|
2
|
+
var X=class{state;listeners=new Set;constructor(e){this.state=this.freezeState({filters:{...e.filters},results:{items:[],nextCursor:null},bounds:null,selection:null,hovered:null,pagination:{mode:e.mode??"paged",loading:!1},layers:{},points:{}})}getState(){return this.state}setFilters(e){this.setState({filters:{...this.state.filters,...e}})}setResults(e){this.setState({results:{items:[...e.items],nextCursor:e.nextCursor,total:e.total}})}appendResults(e){this.setState({results:{items:[...this.state.results.items,...e.items],nextCursor:e.nextCursor,total:e.total}})}setBounds(e){this.setState({bounds:e?{...e}:null})}setSelection(e){this.setState({selection:e})}setHovered(e){this.setState({hovered:e})}setLayerVisible(e,i){this.setState({layers:{...this.state.layers,[e]:i}})}setLoading(e){this.setState({pagination:{...this.state.pagination,loading:e}})}setPoints(e,i){this.setState({points:{...this.state.points,[e]:[...i]}})}subscribe(e){return this.listeners.add(e),()=>{this.listeners.delete(e)}}setState(e){this.state=this.freezeState({...this.state,...e}),this.notify()}notify(){for(let e of this.listeners)e()}freezeState(e){Object.freeze(e.filters),Object.freeze(e.results.items),Object.freeze(e.results),e.bounds&&Object.freeze(e.bounds),Object.freeze(e.pagination),Object.freeze(e.layers);for(let i of Object.values(e.points))Object.freeze(i);return Object.freeze(e.points),Object.freeze(e)}};var z=class{defs=new Map;add(e){if(this.defs.has(e.key))throw new Error(`FilterRegistry: filter "${e.key}" is already registered`);return this.defs.set(e.key,{...e}),this}remove(e){return this.defs.delete(e),this}replace(e,i){if(!this.defs.has(e))throw new Error(`FilterRegistry: cannot replace unregistered filter "${e}"`);return this.defs.set(e,{...i,key:e}),this}reorder(e){let i=this.list(),r=e.filter(s=>this.defs.has(s));r.forEach((s,o)=>{this.defs.get(s).order=o});let n=new Set(r);return i.filter(s=>!n.has(s.key)).forEach((s,o)=>{s.order=r.length+o}),this}list(){return[...this.defs.values()].sort((e,i)=>e.order-i.order)}has(e){return this.defs.has(e)}toFilters(e){return this.list().filter(r=>Object.hasOwn(e,r.key)).map(r=>r.toParams(e[r.key])).reduce((r,n)=>({...r,...n}),{})}activeKeys(e){return this.list().filter(i=>i.isActive?.(e)).map(i=>i.key)}clearedParams(){return this.list().reduce((e,i)=>Object.assign(e,i.toParams(i.fromParams({}))),{})}};var J=class{defs=new Map;add(e){if(this.defs.has(e.id))throw new Error(`DatasetRegistry: dataset "${e.id}" is already registered`);return this.defs.set(e.id,{...e}),this}get(e){return this.defs.get(e)}has(e){return this.defs.has(e)}list(){return[...this.defs.values()]}visibleIds(){return this.list().filter(e=>e.visible?.()!==!1).map(e=>e.id)}};var Y=class{map=new Map;dispose(){this.map.clear()}emit(e){let i=this.map.get(e.type);if(i)for(let n of[...i])n(e);let r=this.map.get("*");if(r)for(let n of[...r])n(e)}on(e,i){let r=this.map.get(e);return r||(r=new Set,this.map.set(e,r)),r.add(i),()=>{r.delete(i)}}};var Re={pagination:"paged",pageSize:20,debounceMs:250};var ee=class{options;constructor(e){this.options=Object.freeze({...Re,...e})}};var te=class{filters;map;datasets;primaryDatasetId;store;emitter=new Y;config;debounceTimer=null;debounceResolve=null;queryToken=0;pointsToken=0;constructor(e){this.datasets=e.datasets,this.filters=e.filters??new z,this.map=e.map,this.config=new ee(e.config);let i=e.primaryDatasetId??this.datasets.list()[0]?.id;if(i==null||!this.datasets.has(i))throw new Error(`ListingEngine: primary dataset "${i??""}" is not registered \u2014 pass a valid primaryDatasetId or register at least one dataset`);this.primaryDatasetId=i,this.store=new X({filters:e.initialFilters??{},mode:this.config.options.pagination})}get state(){return this.store.getState()}get options(){return this.config.options}applyFilters(e){this.store.setFilters(e),this.emitter.emit({type:"FiltersChanged",filters:this.currentFilters()}),this.clearDebounce();let i=++this.queryToken,r=this.config.options.debounceMs;return r<=0?this.runQuery(i):new Promise(n=>{this.debounceResolve=n,this.debounceTimer=setTimeout(()=>{this.debounceTimer=null,this.debounceResolve=null,n(this.runQuery(i))},r)})}async loadPage(){let e=this.state.results.nextCursor;if(e===null)return;let i=++this.queryToken,r=this.primaryDataset();this.store.setLoading(!0);try{let n=await r.adapter.list(this.currentFilters(),{cursor:e,limit:this.config.options.pageSize});if(i!==this.queryToken)return;this.config.options.pagination==="infinite"?this.store.appendResults(n):this.store.setResults(n),this.emitter.emit({type:"ResultsLoaded",datasetId:this.primaryDatasetId,count:n.items.length})}finally{i===this.queryToken&&this.store.setLoading(!1)}}async loadPoints(e){this.store.setBounds(e),this.emitter.emit({type:"BoundsChanged",bounds:e});let i=this.currentFilters(),r=++this.pointsToken;await Promise.allSettled(this.datasets.visibleIds().map(async n=>{let s=this.datasets.get(n);if(!s)return;let o=await s.adapter.getPoints(i,e);r===this.pointsToken&&this.store.setPoints(n,o)}))}selectPoint(e,i){this.store.setSelection(i);let r=this.state.points[e]?.find(n=>n.id===i);r&&this.emitter.emit({type:"PointClicked",datasetId:e,id:r.id,entity:r.entity})}setHovered(e,i){this.store.setHovered(i)}toggleLayer(e){let r=!(this.state.layers[e]??!0);this.store.setLayerVisible(e,r),this.emitter.emit({type:"LayerToggled",datasetId:e,visible:r})}subscribe(e){return this.store.subscribe(e)}on(e,i){return this.emitter.on(e,i)}dispose(){this.clearDebounce(),this.emitter.dispose()}async runQuery(e){if(e!==this.queryToken)return;let i=this.primaryDataset();this.store.setLoading(!0);try{let r=await i.adapter.list(this.currentFilters(),{cursor:null,limit:this.config.options.pageSize});if(e!==this.queryToken)return;this.store.setResults(r),this.emitter.emit({type:"ResultsLoaded",datasetId:this.primaryDatasetId,count:r.items.length})}finally{e===this.queryToken&&this.store.setLoading(!1)}}primaryDataset(){return this.datasets.get(this.primaryDatasetId)}currentFilters(){return this.store.getState().filters}clearDebounce(){this.debounceTimer!==null&&(clearTimeout(this.debounceTimer),this.debounceTimer=null),this.debounceResolve!==null&&(this.debounceResolve(),this.debounceResolve=null)}};function Me(...t){let e={config:{},filters:new z,datasets:new J};for(let i of t)i(e);return e}var De=t=>e=>{e.config={...e.config,...t}},Oe=t=>e=>{e.map=t},_e=t=>e=>{e.datasets.add(t)},Be=t=>e=>{t(e.filters)},Si=t=>e=>{e.urlSync=t},Ae=t=>e=>{e.initialFilters=t},ki=t=>e=>{e.primaryDatasetId=t};import{createContext as ut,useContext as mt}from"react";import{jsx as N,jsxs as Ct}from"react/jsx-runtime";function ft(t){return String(t?.title??"")}var gt=({item:t})=>N("div",{children:ft(t)}),yt=()=>N("div",{}),ce=()=>N("div",{}),vt=({children:t})=>N("div",{children:t}),ht=({children:t})=>N("div",{children:t}),Lt=({value:t,onChange:e,placeholder:i})=>N("input",{type:"search",value:t,placeholder:i,onChange:r=>e(r.target.value),"aria-label":i??"Search"}),bt=()=>N("div",{role:"status",children:"No results"}),Tt=()=>N("div",{role:"status","aria-busy":"true",children:"Loading\u2026"}),Pt=({count:t})=>Ct("div",{children:[t," results"]}),Ft=({children:t})=>N("div",{children:t}),k={Card:gt,Marker:yt,Popup:ce,Sidebar:vt,FilterPanel:ht,Search:Lt,Empty:bt,Loading:Tt,ResultHeader:Pt,Toolbar:Ft},He=ut(k);function ze(t){let{Card:e,Marker:i,Popup:r,Sidebar:n,FilterPanel:s,Search:o,Empty:l,Loading:d,ResultHeader:c,Toolbar:a,children:L}=t,g={Card:e??k.Card,Marker:i??k.Marker,Popup:r??k.Popup,Sidebar:n??k.Sidebar,FilterPanel:s??k.FilterPanel,Search:o??k.Search,Empty:l??k.Empty,Loading:d??k.Loading,ResultHeader:c??k.ResultHeader,Toolbar:a??k.Toolbar};return N(He.Provider,{value:g,children:L})}function F(){return mt(He)}import{createContext as wt}from"react";var ie=wt(null);import{useContext as St}from"react";function y(){let t=St(ie);if(t===null)throw new Error("useListing must be used within a <ListingProvider>");return t}import{useCallback as Ue,useSyncExternalStore as kt}from"react";function C(){let t=y(),e=Ue(r=>t.subscribe(r),[t]),i=Ue(()=>t.state,[t]);return kt(e,i,i)}import{useCallback as Ke}from"react";function re(){let t=y(),e=C(),i=Ke(n=>t.applyFilters(n),[t]),r=Ke((n,s)=>t.applyFilters({[n]:s}),[t]);return{filters:e.filters,set:i,setField:r}}import{jsx as q,jsxs as It}from"react/jsx-runtime";function ue({className:t,groupClassName:e,hideLabels:i,draft:r,onDraftChange:n}={}){let s=y(),{FilterPanel:o}=F(),{filters:l}=re(),d=r!==void 0&&n!==void 0,c=d?r:l;return q(o,{children:q("div",{className:t??"space-y-5",children:s.filters.list().map(a=>{if(typeof a.render=="string")return q("div",{"data-filter":a.key,className:e},a.key);let L=a.render;return It("div",{className:e,children:[a.label&&!i&&q("div",{className:"mb-1.5 text-[13px] font-medium text-foreground",children:a.label}),q(L,{value:a.fromParams(c),onChange:g=>d?n(a.toParams(g)):void s.applyFilters(a.toParams(g))})]},a.key)})})})}function U(){return C().results}import{jsx as ne}from"react/jsx-runtime";function Et(t,e){if(t&&typeof t=="object"&&"id"in t){let i=t.id;if(typeof i=="string"||typeof i=="number")return i}return e}function Ve({className:t}={}){let e=y(),{items:i}=U(),{pagination:r,selection:n}=C(),{Card:s,Empty:o,Loading:l}=F();return r.loading&&i.length===0?ne(l,{}):i.length===0?ne(o,{}):ne("div",{role:"list",className:t,children:i.map((d,c)=>{let a=Et(d,c);return ne(s,{item:d,selected:n===a,onSelect:()=>e.selectPoint(e.primaryDatasetId,a)},a)})})}import{useEffect as j,useRef as _,useState as $e}from"react";import{createPortal as xt}from"react-dom";import{jsx as me,jsxs as je}from"react/jsx-runtime";var Nt={west:-179.9,south:-85,east:179.9,north:85},We=.1,qe=.02;function Rt(t){if(t.length===0)return null;let e=t[0].lng,i=t[0].lng,r=t[0].lat,n=t[0].lat;for(let{lat:l,lng:d}of t)d<e&&(e=d),d>i&&(i=d),l<r&&(r=l),l>n&&(n=l);let s=n>r?(n-r)*We:qe,o=i>e?(i-e)*We:qe;return{west:e-o,east:i+o,south:r-s,north:n+s}}function Qe(t){let{center:e,zoom:i,fallback:r,mapControls:n}=t,s=y(),o=C(),l=_(null),d=_(null),c=_(null),[a,L]=$e(!1),g=_(!1),P=_(!1),O=_(!1),p=s.map;j(()=>{let T=c.current;if(!p||!T)return;let f=[];for(let u of Object.keys(o.points)){if(o.layers[u]===!1)continue;let v=s.datasets.get(u),x=o.points[u]??[],H={id:u,markers:x.map(S=>({id:S.id,position:S.position,iconUrl:v?.marker.iconUrl?.(S.entity),element:v?.marker.element?.(S.entity)})),clustering:v?.clustering,onMarkerClick:S=>s.selectPoint(u,S)};f.push(p.renderLayer(T,H))}return()=>{f.forEach(u=>u())}},[s,p,a,o.points,o.layers]),j(()=>{if(!l.current||!p)return;let T=l.current,f=!1,u=null;return(async()=>{let v=await p.mount(T,{center:e,zoom:i,fullscreenTarget:d.current??void 0});if(f){p.destroy(v);return}c.current=v,u=p.onBoundsChange(v,x=>{O.current?O.current=!1:P.current=!0,s.loadPoints(x)}),L(!0),s.loadPoints(Nt)})(),()=>{f=!0,u?.(),c.current&&(p.destroy(c.current),c.current=null),L(!1)}},[s,p]),j(()=>{let T=c.current;if(!p||!T||e||g.current||P.current)return;let f=[];for(let v of Object.keys(o.points))if(o.layers[v]!==!1)for(let x of o.points[v]??[])f.push(x.position);let u=Rt(f);u&&(g.current=!0,O.current=!0,p.fitBounds(T,u))},[p,e,a,o.points,o.layers]),j(()=>{p?.updateMarkerStates(o.selection,o.hovered)},[p,a,o.selection,o.hovered]);let{Popup:R}=F(),b=R!==ce,$=o.points[s.primaryDatasetId]??[],I=o.selection!=null?$.find(T=>T.id===o.selection):void 0,[E,G]=$e(null),Z=_(I);return Z.current=I,j(()=>{let T=c.current;if(!p||!T||!b)return;let f=Z.current;if(!f)return;let u=p.mountOverlay(f.position);G({entity:f.entity,position:f.position,container:u.container});let v=()=>s.selectPoint(s.primaryDatasetId,null),x=S=>{S.key==="Escape"&&v()};document.addEventListener("keydown",x);let H=p.onMapClick(v);return()=>{document.removeEventListener("keydown",x),H(),u.unmount(),G(null)}},[s,p,a,o.selection,b]),je("div",{ref:d,className:"relative h-full min-h-0 w-full",children:[je("div",{ref:l,className:!p&&r?"flex h-full min-h-0 w-full items-center justify-center":"h-full min-h-0 w-full",children:[!p&&r,b&&E?xt(me(R,{entity:E.entity,onClose:()=>s.selectPoint(s.primaryDatasetId,null)}),E.container):null]}),n!=null&&me("div",{className:"pointer-events-none absolute inset-0",children:me("div",{className:"pointer-events-auto",children:n})})]})}import{jsx as Mt}from"react/jsx-runtime";function Ge(){let t=y(),{results:e,pagination:i}=C();return e.nextCursor==null?null:Mt("button",{type:"button",disabled:i.loading,onClick:()=>{t.loadPage()},children:"Load more"})}import{jsx as Dt}from"react/jsx-runtime";function Ze(){let{items:t,total:e}=U(),{ResultHeader:i}=F();return Dt(i,{count:t.length,total:e})}import{useEffect as Ot,useRef as _t}from"react";function Xe(t,e){let i=y(),r=_t(e);r.current=e,Ot(()=>i.on(t,n=>r.current(n)),[i,t])}import{useEffect as Bt,useState as Je}from"react";import{jsx as At}from"react/jsx-runtime";function Ye(t){let{children:e,...i}=t,[r]=Je(()=>i),[n,s]=Je(null);return Bt(()=>{let o=new te({datasets:r.datasets,filters:r.filters,config:r.config,map:r.map,initialFilters:r.initialFilters,primaryDatasetId:r.primaryDatasetId});return r.urlSync&&r.urlSync.start(o),s(o),()=>{r.urlSync&&r.urlSync.stop(),o.dispose(),s(l=>l===o?null:l)}},[r]),n?At(ie.Provider,{value:n,children:e}):null}function K(t){return typeof t!="number"?t:new Intl.NumberFormat("en-US",{style:"currency",currency:"USD",maximumFractionDigits:0}).format(t)}import{Fragment as zt,jsx as M,jsxs as et}from"react/jsx-runtime";function Ht(t){return t?"rle-card rle-card--selected":"rle-card"}function fe({item:t,selected:e,onSelect:i}){let r=t??{},n=Ht(e),s=et(zt,{children:[r.imageUrl?M("img",{src:r.imageUrl,alt:r.title??"",className:"rle-card-media"}):M("div",{className:"rle-card-media rle-card-media--placeholder","aria-hidden":"true"}),et("div",{className:"rle-card-body",children:[r.title&&M("span",{className:"rle-card-title",children:r.title}),r.subtitle&&M("span",{className:"rle-card-address",children:r.subtitle}),r.badge&&M("div",{className:"rle-card-info",children:M("span",{className:"rle-card-info-item",children:r.badge})}),r.price!=null&&M("span",{className:"rle-card-price",children:K(r.price)})]})]});return i?M("button",{type:"button",onClick:i,"aria-pressed":e??!1,className:n,children:s}):M("article",{className:n,children:s})}import{jsx as se,jsxs as tt}from"react/jsx-runtime";function ge(t){return tt("div",{role:"status",className:"rle-empty",children:[tt("svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:1.5,strokeLinecap:"round",strokeLinejoin:"round",className:"rle-empty-icon","aria-hidden":"true",children:[se("circle",{cx:"11",cy:"11",r:"7"}),se("path",{d:"m21 21-4.3-4.3"})]}),se("p",{className:"rle-empty-title",children:"No results"}),se("p",{className:"rle-empty-hint",children:"Try adjusting your filters or search terms."})]})}import{jsx as Ut}from"react/jsx-runtime";function ye({children:t}){return Ut("div",{className:"rle-filter-panel",children:t})}import{jsx as oe,jsxs as Kt}from"react/jsx-runtime";function ve(t){return oe("div",{className:"rle-loading",role:"status","aria-busy":"true","aria-label":"Loading results",children:Array.from({length:3}).map((e,i)=>Kt("div",{className:"rle-loading-item",children:[oe("div",{className:"rle-skeleton",style:{aspectRatio:"4 / 3",width:"100%"}}),oe("div",{className:"rle-skeleton",style:{height:16,width:"65%"}}),oe("div",{className:"rle-skeleton",style:{height:12,width:"35%"}})]},i))})}import{jsx as Vt}from"react/jsx-runtime";function he({point:t}){let e=t.entity??{};return Vt("span",{className:"rle-pin",children:e.price!=null?K(e.price):""})}import{jsx as V,jsxs as Le}from"react/jsx-runtime";function be({entity:t,onClose:e}){let i=t??{};return Le("div",{className:"rle-popup",role:"group","aria-label":"Location details",children:[V("button",{type:"button",onClick:e,"aria-label":"Close",className:"rle-popup-close",children:Le("svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round",width:"16",height:"16","aria-hidden":"true",children:[V("path",{d:"M18 6 6 18"}),V("path",{d:"m6 6 12 12"})]})}),Le("div",{children:[i.title&&V("div",{className:"rle-card-title",children:i.title}),i.subtitle&&V("div",{className:"rle-card-address",children:i.subtitle}),i.price!=null&&V("div",{className:"rle-card-price",children:K(i.price)})]})]})}import{jsx as $t}from"react/jsx-runtime";function Te({count:t,total:e}){let i=e!=null&&e!==t?`${t} of ${e} results`:`${t} results`;return $t("div",{className:"rle-result-header",children:i})}import{jsx as Wt}from"react/jsx-runtime";function Pe({value:t,onChange:e,placeholder:i}){return Wt("input",{type:"search",value:t,placeholder:i,onChange:r=>e(r.target.value),"aria-label":i??"Search",className:"rle-input"})}import{jsx as qt}from"react/jsx-runtime";function Fe({children:t}){return qt("aside",{className:"rle-sidebar",children:t})}import{jsx as jt}from"react/jsx-runtime";function Ce({children:t}){return jt("div",{className:"rle-toolbar",children:t})}var it={Card:fe,Marker:he,Popup:be,Sidebar:Fe,FilterPanel:ye,Search:Pe,Empty:ge,Loading:ve,ResultHeader:Te,Toolbar:Ce};import{jsx as w,jsxs as Q}from"react/jsx-runtime";function rt({view:t,onViewChange:e}){return w("nav",{className:"rle-bottom-nav","aria-label":"Listing navigation",children:Q("div",{className:"rle-viewtoggle",role:"group","aria-label":"View",children:[Q("button",{type:"button",className:`rle-viewtoggle__btn${t==="list"?" rle-viewtoggle__btn--active":""}`,"aria-pressed":t==="list",onClick:()=>e("list"),children:[w(Qt,{}),"List"]}),Q("button",{type:"button",className:`rle-viewtoggle__btn${t==="map"?" rle-viewtoggle__btn--active":""}`,"aria-pressed":t==="map",onClick:()=>e("map"),children:[w(Gt,{}),"Map"]})]})})}function Qt(){return Q("svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round",width:"16",height:"16","aria-hidden":"true",children:[w("line",{x1:"8",y1:"6",x2:"20",y2:"6"}),w("line",{x1:"8",y1:"12",x2:"20",y2:"12"}),w("line",{x1:"8",y1:"18",x2:"20",y2:"18"}),w("line",{x1:"4",y1:"6",x2:"4.01",y2:"6"}),w("line",{x1:"4",y1:"12",x2:"4.01",y2:"12"}),w("line",{x1:"4",y1:"18",x2:"4.01",y2:"18"})]})}function Gt(){return Q("svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round",width:"16",height:"16","aria-hidden":"true",children:[w("polygon",{points:"1 6 8 3 16 6 23 3 23 18 16 21 8 18 1 21 1 6"}),w("line",{x1:"8",y1:"3",x2:"8",y2:"18"}),w("line",{x1:"16",y1:"6",x2:"16",y2:"21"})]})}import{useEffect as we,useRef as Zt,useState as nt}from"react";import{createPortal as Xt}from"react-dom";import{Fragment as Yt,jsx as D,jsxs as ae}from"react/jsx-runtime";function st({open:t,onOpenChange:e,title:i,children:r,footer:n}){let s=Zt(null),[o,l]=nt(!1),[d,c]=nt(!1);return we(()=>{if(!t){c(!1),l(!1);return}l(!0);let a=requestAnimationFrame(()=>c(!0));return()=>cancelAnimationFrame(a)},[t]),we(()=>{if(!o)return;let a=document.body.style.overflow;return document.body.style.overflow="hidden",()=>{document.body.style.overflow=a}},[o]),we(()=>{if(!o)return;s.current?.focus();function a(L){L.key==="Escape"&&e(!1)}return document.addEventListener("keydown",a),()=>document.removeEventListener("keydown",a)},[o,e]),!o||typeof document>"u"?null:Xt(ae(Yt,{children:[D("div",{className:`rle-sheet-backdrop${d?" rle-sheet-backdrop--open":""}`,onClick:()=>e(!1),"aria-hidden":"true"}),ae("div",{ref:s,className:`rle-sheet${d?" rle-sheet--open":""}`,role:"dialog","aria-modal":"true","aria-label":i,tabIndex:-1,children:[D("div",{className:"rle-sheet__handle","aria-hidden":"true"}),ae("div",{className:"rle-sheet__header",children:[i&&D("div",{className:"rle-sheet__title",children:i}),D("button",{type:"button",className:"rle-sheet__close",onClick:()=>e(!1),"aria-label":"Close",children:D(Jt,{})})]}),D("div",{className:"rle-sheet__body",children:r}),n&&D("div",{className:"rle-sheet__footer",children:n})]})]}),document.body)}function Jt(){return ae("svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round",width:"16",height:"16","aria-hidden":"true",children:[D("path",{d:"M18 6 6 18"}),D("path",{d:"m6 6 12 12"})]})}import{useEffect as Se,useRef as at,useState as A}from"react";import{jsx as h,jsxs as le}from"react/jsx-runtime";function ot({search:t,onFiltersClick:e,filterCount:i=0,action:r}){let{Search:n}=F();return le("header",{className:"rle-mobile-header",children:[t&&h("div",{className:"rle-mobile-header__search",children:h(n,{value:t.value,onChange:t.onChange,placeholder:t.placeholder})}),le("button",{type:"button",className:"rle-btn rle-mobile-header__btn",onClick:e,children:[h(ei,{}),h("span",{children:"Filters"}),i>0&&h("span",{className:"rle-mobile-header__count",children:i})]}),r&&h("button",{type:"button",className:"rle-btn rle-mobile-header__btn rle-mobile-header__btn--icon",onClick:r.onClick,"aria-label":r.label,children:r.icon??h(ti,{})})]})}function ei(){return le("svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round","aria-hidden":"true",children:[h("line",{x1:"4",y1:"6",x2:"20",y2:"6"}),h("circle",{cx:"9",cy:"6",r:"2",fill:"currentColor",stroke:"none"}),h("line",{x1:"4",y1:"12",x2:"20",y2:"12"}),h("circle",{cx:"15",cy:"12",r:"2",fill:"currentColor",stroke:"none"}),h("line",{x1:"4",y1:"18",x2:"20",y2:"18"}),h("circle",{cx:"11",cy:"18",r:"2",fill:"currentColor",stroke:"none"})]})}function ti(){return le("svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round","aria-hidden":"true",children:[h("line",{x1:"12",y1:"5",x2:"12",y2:"19"}),h("line",{x1:"5",y1:"12",x2:"19",y2:"12"})]})}import{Fragment as si,jsx as m,jsxs as B}from"react/jsx-runtime";var ii=m("div",{className:"rle-empty",children:"Map unavailable"});function ri(){let t=at(null),[e,i]=A(!0),[r,n]=A(!0);return Se(()=>{let s=t.current;if(!s)return;let o=()=>{let{clientWidth:L,scrollLeft:g,scrollWidth:P}=s;i(g<=0),n(g+L>=P-1)},l=0,d=()=>{l||(l=requestAnimationFrame(()=>{l=0,o()}))};o(),s.addEventListener("scroll",o,{passive:!0});let c,a;return typeof ResizeObserver<"u"&&(c=new ResizeObserver(o),c.observe(s)),typeof MutationObserver<"u"&&(a=new MutationObserver(d),a.observe(s,{characterData:!0,childList:!0,subtree:!0})),()=>{s.removeEventListener("scroll",o),c?.disconnect(),a?.disconnect(),l&&cancelAnimationFrame(l)}},[]),{atEnd:r,atStart:e,ref:t}}function ni(t,e){if(t===e)return!0;if(typeof t!="object"||t===null||typeof e!="object"||e===null)return!1;let i=t,r=e,n=new Set([...Object.keys(i),...Object.keys(r)]);for(let s of n)if(i[s]!==r[s])return!1;return!0}function lt({search:t,toolbarEnd:e,mobileAction:i,autoFetch:r=!0,hasMap:n,mapCenter:s,mapZoom:o,mapControls:l,mobileSheetFooter:d,className:c}){let a=y(),{Search:L}=F(),g=U(),{filters:P,set:O}=re(),{pagination:p}=C(),R=n??a.map!=null,[b,$]=A("list"),[I,E]=A(!1),{atEnd:G,atStart:Z,ref:T}=ri(),[f,u]=A(P),[v,x]=A(I);I!==v&&(x(I),I&&u(P));let H=pe=>u(ct=>({...ct,...pe})),[S,Ie]=A(!1),de=at(!1);Se(()=>{if(S){if(p.loading){de.current=!0;return}de.current&&(de.current=!1,Ie(!1),E(!1))}},[S,p.loading]);let W=t?{value:String(P[t.filterKey]??""),onChange:pe=>{O({[t.filterKey]:pe||void 0})},placeholder:t.placeholder}:void 0;Se(()=>{r!==!1&&a.applyFilters({})},[a,r]);let Ee=()=>{H(a.filters.clearedParams())},xe=()=>{if(ni(f,P)){E(!1);return}Ie(!0),a.applyFilters(f)},pt=a.filters.activeKeys(P).length,Ne=g.total??g.items.length;return B("div",{className:c?`rle-app ${c}`:"rle-app",children:[B("div",{className:"rle-filter-bar",children:[B("div",{className:"rle-filter-bar__scroll",ref:T,children:[W&&m("div",{className:"rle-filter-bar__search",children:m(L,{value:W.value,onChange:W.onChange,placeholder:W.placeholder})}),m(ue,{className:"rle-filters-row",groupClassName:"rle-filter-group",hideLabels:!0})]}),!Z&&m("div",{className:"rle-filter-bar__fade rle-filter-bar__fade--start","aria-hidden":"true"}),!G&&m("div",{className:"rle-filter-bar__fade rle-filter-bar__fade--end","aria-hidden":"true"})]}),m(ot,{search:W,onFiltersClick:()=>E(!0),filterCount:pt,action:i}),B("div",{className:`rle-body ${R?"rle-split":"rle-body--list-only"}`,"data-mobile-view":b,children:[B("div",{className:"rle-list",children:[B("div",{className:"rle-list-header",children:[m(Ze,{}),e&&m("div",{className:"rle-list-header__toolbar",children:e})]}),m(Ve,{className:"rle-list-grid"}),m(Ge,{})]}),R&&m("div",{className:"rle-map",children:m(Qe,{center:s,zoom:o,fallback:ii,mapControls:l})})]}),R&&m(rt,{view:b,onViewChange:$}),m(st,{title:"Filters",open:I,onOpenChange:E,footer:d?d({draft:f,apply:xe,clear:Ee,resultCount:Ne,loading:p.loading}):B(si,{children:[m("button",{type:"button",className:"rle-btn rle-btn--ghost",onClick:Ee,children:"Clear all"}),m("button",{type:"button",className:"rle-btn rle-btn--primary rle-sheet__apply",disabled:p.loading,onClick:xe,children:p.loading?m("span",{className:"rle-spinner","aria-label":"Updating results"}):`Show ${Ne} results`})]}),children:m(ue,{className:"rle-filter-stack",groupClassName:"rle-filter-group",draft:f,onDraftChange:H})})]})}import{useEffect as oi,useRef as ai,useState as li}from"react";import{jsx as ke,jsxs as ci}from"react/jsx-runtime";function dt(t){return"provider"in t}function di(t){let e=t!=null&&!dt(t),i=e?t.apiKey:void 0,r=e?t.mapId:void 0,n=e?t.mapOptions:void 0,s=e?t.styles:void 0,[o,l]=li(()=>!t||dt(t)?{ready:!0,provider:t?.provider}:{ready:!1});return oi(()=>{if(!i)return;let d=!1;return import("./maps/google/index.js").then(({googleProvider:c})=>{d||l({ready:!0,provider:c({apiKey:i,mapId:r,mapOptions:n,styles:s})})}),()=>{d=!0}},[i,r]),o}function pi({onFiltersChange:t}){let e=ai(t);return e.current=t,Xe("FiltersChanged",i=>{i.type==="FiltersChanged"&&e.current(i.filters)}),null}function Nn(t){let{datasets:e,filters:i,map:r,components:n,initialFilters:s,onFiltersChange:o,mobileAction:l,search:d,toolbarEnd:c,mapControls:a,mobileSheetFooter:L,config:g,autoFetch:P,className:O}=t,{ready:p,provider:R}=di(r);if(!p)return null;let b=[];for(let E of e)b.push(_e(E));i&&b.push(Be(i)),R&&b.push(Oe(R)),s&&b.push(Ae(s)),g&&b.push(De(g));let $=Me(...b),I={...it,...n};return ci(Ye,{...$,children:[o&&ke(pi,{onFiltersChange:o}),ke(ze,{...I,children:ke(lt,{className:O,search:d,toolbarEnd:c,mobileAction:l,autoFetch:P,mapCenter:r?.center,mapZoom:r?.zoom,mapControls:a,mobileSheetFooter:L})})]})}export{X as a,z as b,J as c,Y as d,Re as e,ee as f,te as g,Me as h,De as i,Oe as j,_e as k,Be as l,Si as m,Ae as n,ki as o,ce as p,ze as q,F as r,ie as s,y as t,C as u,re as v,ue as w,U as x,Ve as y,Qe as z,Ge as A,Ze as B,Xe as C,Ye as D,fe as E,ge as F,ye as G,ve as H,he as I,be as J,Te as K,Pe as L,Fe as M,Ce as N,it as O,rt as P,st as Q,lt as R,Nn as S};
|
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
"use strict";Object.defineProperty(exports, "__esModule", {value: true}); function _interopRequireWildcard(obj) { if (obj && obj.__esModule) { return obj; } else { var newObj = {}; if (obj != null) { for (var key in obj) { if (Object.prototype.hasOwnProperty.call(obj, key)) { newObj[key] = obj[key]; } } } newObj.default = obj; return newObj; } } function _nullishCoalesce(lhs, rhsFn) { if (lhs != null) { return lhs; } else { return rhsFn(); } } function _optionalChain(ops) { let lastAccessLHS = undefined; let value = ops[0]; let i = 1; while (i < ops.length) { const op = ops[i]; const fn = ops[i + 1]; i += 2; if ((op === 'optionalAccess' || op === 'optionalCall') && value == null) { return undefined; } if (op === 'access' || op === 'optionalAccess') { lastAccessLHS = value; value = fn(value); } else if (op === 'call' || op === 'optionalCall') { value = fn((...args) => value.call(lastAccessLHS, ...args)); lastAccessLHS = undefined; } } return value; } var _class; var _class2; var _class3; var _class4; var _class5;"use client";
|
|
2
|
+
var X= (_class =class{__init() {this.listeners=new Set}constructor(e){;_class.prototype.__init.call(this);this.state=this.freezeState({filters:{...e.filters},results:{items:[],nextCursor:null},bounds:null,selection:null,hovered:null,pagination:{mode:_nullishCoalesce(e.mode, () => ("paged")),loading:!1},layers:{},points:{}})}getState(){return this.state}setFilters(e){this.setState({filters:{...this.state.filters,...e}})}setResults(e){this.setState({results:{items:[...e.items],nextCursor:e.nextCursor,total:e.total}})}appendResults(e){this.setState({results:{items:[...this.state.results.items,...e.items],nextCursor:e.nextCursor,total:e.total}})}setBounds(e){this.setState({bounds:e?{...e}:null})}setSelection(e){this.setState({selection:e})}setHovered(e){this.setState({hovered:e})}setLayerVisible(e,i){this.setState({layers:{...this.state.layers,[e]:i}})}setLoading(e){this.setState({pagination:{...this.state.pagination,loading:e}})}setPoints(e,i){this.setState({points:{...this.state.points,[e]:[...i]}})}subscribe(e){return this.listeners.add(e),()=>{this.listeners.delete(e)}}setState(e){this.state=this.freezeState({...this.state,...e}),this.notify()}notify(){for(let e of this.listeners)e()}freezeState(e){Object.freeze(e.filters),Object.freeze(e.results.items),Object.freeze(e.results),e.bounds&&Object.freeze(e.bounds),Object.freeze(e.pagination),Object.freeze(e.layers);for(let i of Object.values(e.points))Object.freeze(i);return Object.freeze(e.points),Object.freeze(e)}}, _class);var z= (_class2 =class{constructor() { _class2.prototype.__init2.call(this); }__init2() {this.defs=new Map}add(e){if(this.defs.has(e.key))throw new Error(`FilterRegistry: filter "${e.key}" is already registered`);return this.defs.set(e.key,{...e}),this}remove(e){return this.defs.delete(e),this}replace(e,i){if(!this.defs.has(e))throw new Error(`FilterRegistry: cannot replace unregistered filter "${e}"`);return this.defs.set(e,{...i,key:e}),this}reorder(e){let i=this.list(),r=e.filter(s=>this.defs.has(s));r.forEach((s,o)=>{this.defs.get(s).order=o});let n=new Set(r);return i.filter(s=>!n.has(s.key)).forEach((s,o)=>{s.order=r.length+o}),this}list(){return[...this.defs.values()].sort((e,i)=>e.order-i.order)}has(e){return this.defs.has(e)}toFilters(e){return this.list().filter(r=>Object.hasOwn(e,r.key)).map(r=>r.toParams(e[r.key])).reduce((r,n)=>({...r,...n}),{})}activeKeys(e){return this.list().filter(i=>_optionalChain([i, 'access', _2 => _2.isActive, 'optionalCall', _3 => _3(e)])).map(i=>i.key)}clearedParams(){return this.list().reduce((e,i)=>Object.assign(e,i.toParams(i.fromParams({}))),{})}}, _class2);var J= (_class3 =class{constructor() { _class3.prototype.__init3.call(this); }__init3() {this.defs=new Map}add(e){if(this.defs.has(e.id))throw new Error(`DatasetRegistry: dataset "${e.id}" is already registered`);return this.defs.set(e.id,{...e}),this}get(e){return this.defs.get(e)}has(e){return this.defs.has(e)}list(){return[...this.defs.values()]}visibleIds(){return this.list().filter(e=>_optionalChain([e, 'access', _4 => _4.visible, 'optionalCall', _5 => _5()])!==!1).map(e=>e.id)}}, _class3);var Y= (_class4 =class{constructor() { _class4.prototype.__init4.call(this); }__init4() {this.map=new Map}dispose(){this.map.clear()}emit(e){let i=this.map.get(e.type);if(i)for(let n of[...i])n(e);let r=this.map.get("*");if(r)for(let n of[...r])n(e)}on(e,i){let r=this.map.get(e);return r||(r=new Set,this.map.set(e,r)),r.add(i),()=>{r.delete(i)}}}, _class4);var Re={pagination:"paged",pageSize:20,debounceMs:250};var ee=class{constructor(e){this.options=Object.freeze({...Re,...e})}};var te= (_class5 =class{__init5() {this.emitter=new Y}__init6() {this.debounceTimer=null}__init7() {this.debounceResolve=null}__init8() {this.queryToken=0}__init9() {this.pointsToken=0}constructor(e){;_class5.prototype.__init5.call(this);_class5.prototype.__init6.call(this);_class5.prototype.__init7.call(this);_class5.prototype.__init8.call(this);_class5.prototype.__init9.call(this);this.datasets=e.datasets,this.filters=_nullishCoalesce(e.filters, () => (new z)),this.map=e.map,this.config=new ee(e.config);let i=_nullishCoalesce(e.primaryDatasetId, () => (_optionalChain([this, 'access', _6 => _6.datasets, 'access', _7 => _7.list, 'call', _8 => _8(), 'access', _9 => _9[0], 'optionalAccess', _10 => _10.id])));if(i==null||!this.datasets.has(i))throw new Error(`ListingEngine: primary dataset "${_nullishCoalesce(i, () => (""))}" is not registered \u2014 pass a valid primaryDatasetId or register at least one dataset`);this.primaryDatasetId=i,this.store=new X({filters:_nullishCoalesce(e.initialFilters, () => ({})),mode:this.config.options.pagination})}get state(){return this.store.getState()}get options(){return this.config.options}applyFilters(e){this.store.setFilters(e),this.emitter.emit({type:"FiltersChanged",filters:this.currentFilters()}),this.clearDebounce();let i=++this.queryToken,r=this.config.options.debounceMs;return r<=0?this.runQuery(i):new Promise(n=>{this.debounceResolve=n,this.debounceTimer=setTimeout(()=>{this.debounceTimer=null,this.debounceResolve=null,n(this.runQuery(i))},r)})}async loadPage(){let e=this.state.results.nextCursor;if(e===null)return;let i=++this.queryToken,r=this.primaryDataset();this.store.setLoading(!0);try{let n=await r.adapter.list(this.currentFilters(),{cursor:e,limit:this.config.options.pageSize});if(i!==this.queryToken)return;this.config.options.pagination==="infinite"?this.store.appendResults(n):this.store.setResults(n),this.emitter.emit({type:"ResultsLoaded",datasetId:this.primaryDatasetId,count:n.items.length})}finally{i===this.queryToken&&this.store.setLoading(!1)}}async loadPoints(e){this.store.setBounds(e),this.emitter.emit({type:"BoundsChanged",bounds:e});let i=this.currentFilters(),r=++this.pointsToken;await Promise.allSettled(this.datasets.visibleIds().map(async n=>{let s=this.datasets.get(n);if(!s)return;let o=await s.adapter.getPoints(i,e);r===this.pointsToken&&this.store.setPoints(n,o)}))}selectPoint(e,i){this.store.setSelection(i);let r=_optionalChain([this, 'access', _11 => _11.state, 'access', _12 => _12.points, 'access', _13 => _13[e], 'optionalAccess', _14 => _14.find, 'call', _15 => _15(n=>n.id===i)]);r&&this.emitter.emit({type:"PointClicked",datasetId:e,id:r.id,entity:r.entity})}setHovered(e,i){this.store.setHovered(i)}toggleLayer(e){let r=!(_nullishCoalesce(this.state.layers[e], () => (!0)));this.store.setLayerVisible(e,r),this.emitter.emit({type:"LayerToggled",datasetId:e,visible:r})}subscribe(e){return this.store.subscribe(e)}on(e,i){return this.emitter.on(e,i)}dispose(){this.clearDebounce(),this.emitter.dispose()}async runQuery(e){if(e!==this.queryToken)return;let i=this.primaryDataset();this.store.setLoading(!0);try{let r=await i.adapter.list(this.currentFilters(),{cursor:null,limit:this.config.options.pageSize});if(e!==this.queryToken)return;this.store.setResults(r),this.emitter.emit({type:"ResultsLoaded",datasetId:this.primaryDatasetId,count:r.items.length})}finally{e===this.queryToken&&this.store.setLoading(!1)}}primaryDataset(){return this.datasets.get(this.primaryDatasetId)}currentFilters(){return this.store.getState().filters}clearDebounce(){this.debounceTimer!==null&&(clearTimeout(this.debounceTimer),this.debounceTimer=null),this.debounceResolve!==null&&(this.debounceResolve(),this.debounceResolve=null)}}, _class5);function Me(...t){let e={config:{},filters:new z,datasets:new J};for(let i of t)i(e);return e}var De=t=>e=>{e.config={...e.config,...t}},Oe= exports.j =t=>e=>{e.map=t},_e= exports.k =t=>e=>{e.datasets.add(t)},Be= exports.l =t=>e=>{t(e.filters)},Si= exports.m =t=>e=>{e.urlSync=t},Ae= exports.n =t=>e=>{e.initialFilters=t},ki= exports.o =t=>e=>{e.primaryDatasetId=t};var _react = require('react');var _jsxruntime = require('react/jsx-runtime');function ft(t){return String(_nullishCoalesce(_optionalChain([t, 'optionalAccess', _16 => _16.title]), () => ("")))}var gt=({item:t})=>_jsxruntime.jsx.call(void 0, "div",{children:ft(t)}),yt=()=>_jsxruntime.jsx.call(void 0, "div",{}),ce= exports.p =()=>_jsxruntime.jsx.call(void 0, "div",{}),vt=({children:t})=>_jsxruntime.jsx.call(void 0, "div",{children:t}),ht=({children:t})=>_jsxruntime.jsx.call(void 0, "div",{children:t}),Lt=({value:t,onChange:e,placeholder:i})=>_jsxruntime.jsx.call(void 0, "input",{type:"search",value:t,placeholder:i,onChange:r=>e(r.target.value),"aria-label":_nullishCoalesce(i, () => ("Search"))}),bt=()=>_jsxruntime.jsx.call(void 0, "div",{role:"status",children:"No results"}),Tt=()=>_jsxruntime.jsx.call(void 0, "div",{role:"status","aria-busy":"true",children:"Loading\u2026"}),Pt=({count:t})=>_jsxruntime.jsxs.call(void 0, "div",{children:[t," results"]}),Ft=({children:t})=>_jsxruntime.jsx.call(void 0, "div",{children:t}),k={Card:gt,Marker:yt,Popup:ce,Sidebar:vt,FilterPanel:ht,Search:Lt,Empty:bt,Loading:Tt,ResultHeader:Pt,Toolbar:Ft},He=_react.createContext.call(void 0, k);function ze(t){let{Card:e,Marker:i,Popup:r,Sidebar:n,FilterPanel:s,Search:o,Empty:l,Loading:d,ResultHeader:c,Toolbar:a,children:L}=t,g={Card:_nullishCoalesce(e, () => (k.Card)),Marker:_nullishCoalesce(i, () => (k.Marker)),Popup:_nullishCoalesce(r, () => (k.Popup)),Sidebar:_nullishCoalesce(n, () => (k.Sidebar)),FilterPanel:_nullishCoalesce(s, () => (k.FilterPanel)),Search:_nullishCoalesce(o, () => (k.Search)),Empty:_nullishCoalesce(l, () => (k.Empty)),Loading:_nullishCoalesce(d, () => (k.Loading)),ResultHeader:_nullishCoalesce(c, () => (k.ResultHeader)),Toolbar:_nullishCoalesce(a, () => (k.Toolbar))};return _jsxruntime.jsx.call(void 0, He.Provider,{value:g,children:L})}function F(){return _react.useContext.call(void 0, He)}var ie=_react.createContext.call(void 0, null);function y(){let t=_react.useContext.call(void 0, ie);if(t===null)throw new Error("useListing must be used within a <ListingProvider>");return t}function C(){let t=y(),e=_react.useCallback.call(void 0, r=>t.subscribe(r),[t]),i=_react.useCallback.call(void 0, ()=>t.state,[t]);return _react.useSyncExternalStore.call(void 0, e,i,i)}function re(){let t=y(),e=C(),i=_react.useCallback.call(void 0, n=>t.applyFilters(n),[t]),r=_react.useCallback.call(void 0, (n,s)=>t.applyFilters({[n]:s}),[t]);return{filters:e.filters,set:i,setField:r}}function ue({className:t,groupClassName:e,hideLabels:i,draft:r,onDraftChange:n}={}){let s=y(),{FilterPanel:o}=F(),{filters:l}=re(),d=r!==void 0&&n!==void 0,c=d?r:l;return _jsxruntime.jsx.call(void 0, o,{children:_jsxruntime.jsx.call(void 0, "div",{className:_nullishCoalesce(t, () => ("space-y-5")),children:s.filters.list().map(a=>{if(typeof a.render=="string")return _jsxruntime.jsx.call(void 0, "div",{"data-filter":a.key,className:e},a.key);let L=a.render;return _jsxruntime.jsxs.call(void 0, "div",{className:e,children:[a.label&&!i&&_jsxruntime.jsx.call(void 0, "div",{className:"mb-1.5 text-[13px] font-medium text-foreground",children:a.label}),_jsxruntime.jsx.call(void 0, L,{value:a.fromParams(c),onChange:g=>d?n(a.toParams(g)):void s.applyFilters(a.toParams(g))})]},a.key)})})})}function U(){return C().results}function Et(t,e){if(t&&typeof t=="object"&&"id"in t){let i=t.id;if(typeof i=="string"||typeof i=="number")return i}return e}function Ve({className:t}={}){let e=y(),{items:i}=U(),{pagination:r,selection:n}=C(),{Card:s,Empty:o,Loading:l}=F();return r.loading&&i.length===0?_jsxruntime.jsx.call(void 0, l,{}):i.length===0?_jsxruntime.jsx.call(void 0, o,{}):_jsxruntime.jsx.call(void 0, "div",{role:"list",className:t,children:i.map((d,c)=>{let a=Et(d,c);return _jsxruntime.jsx.call(void 0, s,{item:d,selected:n===a,onSelect:()=>e.selectPoint(e.primaryDatasetId,a)},a)})})}var _reactdom = require('react-dom');var Nt={west:-179.9,south:-85,east:179.9,north:85},We=.1,qe=.02;function Rt(t){if(t.length===0)return null;let e=t[0].lng,i=t[0].lng,r=t[0].lat,n=t[0].lat;for(let{lat:l,lng:d}of t)d<e&&(e=d),d>i&&(i=d),l<r&&(r=l),l>n&&(n=l);let s=n>r?(n-r)*We:qe,o=i>e?(i-e)*We:qe;return{west:e-o,east:i+o,south:r-s,north:n+s}}function Qe(t){let{center:e,zoom:i,fallback:r,mapControls:n}=t,s=y(),o=C(),l=_react.useRef.call(void 0, null),d=_react.useRef.call(void 0, null),c=_react.useRef.call(void 0, null),[a,L]=_react.useState.call(void 0, !1),g=_react.useRef.call(void 0, !1),P=_react.useRef.call(void 0, !1),O=_react.useRef.call(void 0, !1),p=s.map;_react.useEffect.call(void 0, ()=>{let T=c.current;if(!p||!T)return;let f=[];for(let u of Object.keys(o.points)){if(o.layers[u]===!1)continue;let v=s.datasets.get(u),x=_nullishCoalesce(o.points[u], () => ([])),H={id:u,markers:x.map(S=>({id:S.id,position:S.position,iconUrl:_optionalChain([v, 'optionalAccess', _17 => _17.marker, 'access', _18 => _18.iconUrl, 'optionalCall', _19 => _19(S.entity)]),element:_optionalChain([v, 'optionalAccess', _20 => _20.marker, 'access', _21 => _21.element, 'optionalCall', _22 => _22(S.entity)])})),clustering:_optionalChain([v, 'optionalAccess', _23 => _23.clustering]),onMarkerClick:S=>s.selectPoint(u,S)};f.push(p.renderLayer(T,H))}return()=>{f.forEach(u=>u())}},[s,p,a,o.points,o.layers]),_react.useEffect.call(void 0, ()=>{if(!l.current||!p)return;let T=l.current,f=!1,u=null;return(async()=>{let v=await p.mount(T,{center:e,zoom:i,fullscreenTarget:_nullishCoalesce(d.current, () => (void 0))});if(f){p.destroy(v);return}c.current=v,u=p.onBoundsChange(v,x=>{O.current?O.current=!1:P.current=!0,s.loadPoints(x)}),L(!0),s.loadPoints(Nt)})(),()=>{f=!0,_optionalChain([u, 'optionalCall', _24 => _24()]),c.current&&(p.destroy(c.current),c.current=null),L(!1)}},[s,p]),_react.useEffect.call(void 0, ()=>{let T=c.current;if(!p||!T||e||g.current||P.current)return;let f=[];for(let v of Object.keys(o.points))if(o.layers[v]!==!1)for(let x of _nullishCoalesce(o.points[v], () => ([])))f.push(x.position);let u=Rt(f);u&&(g.current=!0,O.current=!0,p.fitBounds(T,u))},[p,e,a,o.points,o.layers]),_react.useEffect.call(void 0, ()=>{_optionalChain([p, 'optionalAccess', _25 => _25.updateMarkerStates, 'call', _26 => _26(o.selection,o.hovered)])},[p,a,o.selection,o.hovered]);let{Popup:R}=F(),b=R!==ce,$=_nullishCoalesce(o.points[s.primaryDatasetId], () => ([])),I=o.selection!=null?$.find(T=>T.id===o.selection):void 0,[E,G]=_react.useState.call(void 0, null),Z=_react.useRef.call(void 0, I);return Z.current=I,_react.useEffect.call(void 0, ()=>{let T=c.current;if(!p||!T||!b)return;let f=Z.current;if(!f)return;let u=p.mountOverlay(f.position);G({entity:f.entity,position:f.position,container:u.container});let v=()=>s.selectPoint(s.primaryDatasetId,null),x=S=>{S.key==="Escape"&&v()};document.addEventListener("keydown",x);let H=p.onMapClick(v);return()=>{document.removeEventListener("keydown",x),H(),u.unmount(),G(null)}},[s,p,a,o.selection,b]),_jsxruntime.jsxs.call(void 0, "div",{ref:d,className:"relative h-full min-h-0 w-full",children:[_jsxruntime.jsxs.call(void 0, "div",{ref:l,className:!p&&r?"flex h-full min-h-0 w-full items-center justify-center":"h-full min-h-0 w-full",children:[!p&&r,b&&E?_reactdom.createPortal.call(void 0, _jsxruntime.jsx.call(void 0, R,{entity:E.entity,onClose:()=>s.selectPoint(s.primaryDatasetId,null)}),E.container):null]}),n!=null&&_jsxruntime.jsx.call(void 0, "div",{className:"pointer-events-none absolute inset-0",children:_jsxruntime.jsx.call(void 0, "div",{className:"pointer-events-auto",children:n})})]})}function Ge(){let t=y(),{results:e,pagination:i}=C();return e.nextCursor==null?null:_jsxruntime.jsx.call(void 0, "button",{type:"button",disabled:i.loading,onClick:()=>{t.loadPage()},children:"Load more"})}function Ze(){let{items:t,total:e}=U(),{ResultHeader:i}=F();return _jsxruntime.jsx.call(void 0, i,{count:t.length,total:e})}function Xe(t,e){let i=y(),r=_react.useRef.call(void 0, e);r.current=e,_react.useEffect.call(void 0, ()=>i.on(t,n=>r.current(n)),[i,t])}function Ye(t){let{children:e,...i}=t,[r]=_react.useState.call(void 0, ()=>i),[n,s]=_react.useState.call(void 0, null);return _react.useEffect.call(void 0, ()=>{let o=new te({datasets:r.datasets,filters:r.filters,config:r.config,map:r.map,initialFilters:r.initialFilters,primaryDatasetId:r.primaryDatasetId});return r.urlSync&&r.urlSync.start(o),s(o),()=>{r.urlSync&&r.urlSync.stop(),o.dispose(),s(l=>l===o?null:l)}},[r]),n?_jsxruntime.jsx.call(void 0, ie.Provider,{value:n,children:e}):null}function K(t){return typeof t!="number"?t:new Intl.NumberFormat("en-US",{style:"currency",currency:"USD",maximumFractionDigits:0}).format(t)}function Ht(t){return t?"rle-card rle-card--selected":"rle-card"}function fe({item:t,selected:e,onSelect:i}){let r=_nullishCoalesce(t, () => ({})),n=Ht(e),s=_jsxruntime.jsxs.call(void 0, _jsxruntime.Fragment,{children:[r.imageUrl?_jsxruntime.jsx.call(void 0, "img",{src:r.imageUrl,alt:_nullishCoalesce(r.title, () => ("")),className:"rle-card-media"}):_jsxruntime.jsx.call(void 0, "div",{className:"rle-card-media rle-card-media--placeholder","aria-hidden":"true"}),_jsxruntime.jsxs.call(void 0, "div",{className:"rle-card-body",children:[r.title&&_jsxruntime.jsx.call(void 0, "span",{className:"rle-card-title",children:r.title}),r.subtitle&&_jsxruntime.jsx.call(void 0, "span",{className:"rle-card-address",children:r.subtitle}),r.badge&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-card-info",children:_jsxruntime.jsx.call(void 0, "span",{className:"rle-card-info-item",children:r.badge})}),r.price!=null&&_jsxruntime.jsx.call(void 0, "span",{className:"rle-card-price",children:K(r.price)})]})]});return i?_jsxruntime.jsx.call(void 0, "button",{type:"button",onClick:i,"aria-pressed":_nullishCoalesce(e, () => (!1)),className:n,children:s}):_jsxruntime.jsx.call(void 0, "article",{className:n,children:s})}function ge(t){return _jsxruntime.jsxs.call(void 0, "div",{role:"status",className:"rle-empty",children:[_jsxruntime.jsxs.call(void 0, "svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:1.5,strokeLinecap:"round",strokeLinejoin:"round",className:"rle-empty-icon","aria-hidden":"true",children:[_jsxruntime.jsx.call(void 0, "circle",{cx:"11",cy:"11",r:"7"}),_jsxruntime.jsx.call(void 0, "path",{d:"m21 21-4.3-4.3"})]}),_jsxruntime.jsx.call(void 0, "p",{className:"rle-empty-title",children:"No results"}),_jsxruntime.jsx.call(void 0, "p",{className:"rle-empty-hint",children:"Try adjusting your filters or search terms."})]})}function ye({children:t}){return _jsxruntime.jsx.call(void 0, "div",{className:"rle-filter-panel",children:t})}function ve(t){return _jsxruntime.jsx.call(void 0, "div",{className:"rle-loading",role:"status","aria-busy":"true","aria-label":"Loading results",children:Array.from({length:3}).map((e,i)=>_jsxruntime.jsxs.call(void 0, "div",{className:"rle-loading-item",children:[_jsxruntime.jsx.call(void 0, "div",{className:"rle-skeleton",style:{aspectRatio:"4 / 3",width:"100%"}}),_jsxruntime.jsx.call(void 0, "div",{className:"rle-skeleton",style:{height:16,width:"65%"}}),_jsxruntime.jsx.call(void 0, "div",{className:"rle-skeleton",style:{height:12,width:"35%"}})]},i))})}function he({point:t}){let e=_nullishCoalesce(t.entity, () => ({}));return _jsxruntime.jsx.call(void 0, "span",{className:"rle-pin",children:e.price!=null?K(e.price):""})}function be({entity:t,onClose:e}){let i=_nullishCoalesce(t, () => ({}));return _jsxruntime.jsxs.call(void 0, "div",{className:"rle-popup",role:"group","aria-label":"Location details",children:[_jsxruntime.jsx.call(void 0, "button",{type:"button",onClick:e,"aria-label":"Close",className:"rle-popup-close",children:_jsxruntime.jsxs.call(void 0, "svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round",width:"16",height:"16","aria-hidden":"true",children:[_jsxruntime.jsx.call(void 0, "path",{d:"M18 6 6 18"}),_jsxruntime.jsx.call(void 0, "path",{d:"m6 6 12 12"})]})}),_jsxruntime.jsxs.call(void 0, "div",{children:[i.title&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-card-title",children:i.title}),i.subtitle&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-card-address",children:i.subtitle}),i.price!=null&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-card-price",children:K(i.price)})]})]})}function Te({count:t,total:e}){let i=e!=null&&e!==t?`${t} of ${e} results`:`${t} results`;return _jsxruntime.jsx.call(void 0, "div",{className:"rle-result-header",children:i})}function Pe({value:t,onChange:e,placeholder:i}){return _jsxruntime.jsx.call(void 0, "input",{type:"search",value:t,placeholder:i,onChange:r=>e(r.target.value),"aria-label":_nullishCoalesce(i, () => ("Search")),className:"rle-input"})}function Fe({children:t}){return _jsxruntime.jsx.call(void 0, "aside",{className:"rle-sidebar",children:t})}function Ce({children:t}){return _jsxruntime.jsx.call(void 0, "div",{className:"rle-toolbar",children:t})}var it={Card:fe,Marker:he,Popup:be,Sidebar:Fe,FilterPanel:ye,Search:Pe,Empty:ge,Loading:ve,ResultHeader:Te,Toolbar:Ce};function rt({view:t,onViewChange:e}){return _jsxruntime.jsx.call(void 0, "nav",{className:"rle-bottom-nav","aria-label":"Listing navigation",children:_jsxruntime.jsxs.call(void 0, "div",{className:"rle-viewtoggle",role:"group","aria-label":"View",children:[_jsxruntime.jsxs.call(void 0, "button",{type:"button",className:`rle-viewtoggle__btn${t==="list"?" rle-viewtoggle__btn--active":""}`,"aria-pressed":t==="list",onClick:()=>e("list"),children:[_jsxruntime.jsx.call(void 0, Qt,{}),"List"]}),_jsxruntime.jsxs.call(void 0, "button",{type:"button",className:`rle-viewtoggle__btn${t==="map"?" rle-viewtoggle__btn--active":""}`,"aria-pressed":t==="map",onClick:()=>e("map"),children:[_jsxruntime.jsx.call(void 0, Gt,{}),"Map"]})]})})}function Qt(){return _jsxruntime.jsxs.call(void 0, "svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round",width:"16",height:"16","aria-hidden":"true",children:[_jsxruntime.jsx.call(void 0, "line",{x1:"8",y1:"6",x2:"20",y2:"6"}),_jsxruntime.jsx.call(void 0, "line",{x1:"8",y1:"12",x2:"20",y2:"12"}),_jsxruntime.jsx.call(void 0, "line",{x1:"8",y1:"18",x2:"20",y2:"18"}),_jsxruntime.jsx.call(void 0, "line",{x1:"4",y1:"6",x2:"4.01",y2:"6"}),_jsxruntime.jsx.call(void 0, "line",{x1:"4",y1:"12",x2:"4.01",y2:"12"}),_jsxruntime.jsx.call(void 0, "line",{x1:"4",y1:"18",x2:"4.01",y2:"18"})]})}function Gt(){return _jsxruntime.jsxs.call(void 0, "svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round",width:"16",height:"16","aria-hidden":"true",children:[_jsxruntime.jsx.call(void 0, "polygon",{points:"1 6 8 3 16 6 23 3 23 18 16 21 8 18 1 21 1 6"}),_jsxruntime.jsx.call(void 0, "line",{x1:"8",y1:"3",x2:"8",y2:"18"}),_jsxruntime.jsx.call(void 0, "line",{x1:"16",y1:"6",x2:"16",y2:"21"})]})}function st({open:t,onOpenChange:e,title:i,children:r,footer:n}){let s=_react.useRef.call(void 0, null),[o,l]=_react.useState.call(void 0, !1),[d,c]=_react.useState.call(void 0, !1);return _react.useEffect.call(void 0, ()=>{if(!t){c(!1),l(!1);return}l(!0);let a=requestAnimationFrame(()=>c(!0));return()=>cancelAnimationFrame(a)},[t]),_react.useEffect.call(void 0, ()=>{if(!o)return;let a=document.body.style.overflow;return document.body.style.overflow="hidden",()=>{document.body.style.overflow=a}},[o]),_react.useEffect.call(void 0, ()=>{if(!o)return;_optionalChain([s, 'access', _27 => _27.current, 'optionalAccess', _28 => _28.focus, 'call', _29 => _29()]);function a(L){L.key==="Escape"&&e(!1)}return document.addEventListener("keydown",a),()=>document.removeEventListener("keydown",a)},[o,e]),!o||typeof document>"u"?null:_reactdom.createPortal.call(void 0, _jsxruntime.jsxs.call(void 0, _jsxruntime.Fragment,{children:[_jsxruntime.jsx.call(void 0, "div",{className:`rle-sheet-backdrop${d?" rle-sheet-backdrop--open":""}`,onClick:()=>e(!1),"aria-hidden":"true"}),_jsxruntime.jsxs.call(void 0, "div",{ref:s,className:`rle-sheet${d?" rle-sheet--open":""}`,role:"dialog","aria-modal":"true","aria-label":i,tabIndex:-1,children:[_jsxruntime.jsx.call(void 0, "div",{className:"rle-sheet__handle","aria-hidden":"true"}),_jsxruntime.jsxs.call(void 0, "div",{className:"rle-sheet__header",children:[i&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-sheet__title",children:i}),_jsxruntime.jsx.call(void 0, "button",{type:"button",className:"rle-sheet__close",onClick:()=>e(!1),"aria-label":"Close",children:_jsxruntime.jsx.call(void 0, Jt,{})})]}),_jsxruntime.jsx.call(void 0, "div",{className:"rle-sheet__body",children:r}),n&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-sheet__footer",children:n})]})]}),document.body)}function Jt(){return _jsxruntime.jsxs.call(void 0, "svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round",width:"16",height:"16","aria-hidden":"true",children:[_jsxruntime.jsx.call(void 0, "path",{d:"M18 6 6 18"}),_jsxruntime.jsx.call(void 0, "path",{d:"m6 6 12 12"})]})}function ot({search:t,onFiltersClick:e,filterCount:i=0,action:r}){let{Search:n}=F();return _jsxruntime.jsxs.call(void 0, "header",{className:"rle-mobile-header",children:[t&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-mobile-header__search",children:_jsxruntime.jsx.call(void 0, n,{value:t.value,onChange:t.onChange,placeholder:t.placeholder})}),_jsxruntime.jsxs.call(void 0, "button",{type:"button",className:"rle-btn rle-mobile-header__btn",onClick:e,children:[_jsxruntime.jsx.call(void 0, ei,{}),_jsxruntime.jsx.call(void 0, "span",{children:"Filters"}),i>0&&_jsxruntime.jsx.call(void 0, "span",{className:"rle-mobile-header__count",children:i})]}),r&&_jsxruntime.jsx.call(void 0, "button",{type:"button",className:"rle-btn rle-mobile-header__btn rle-mobile-header__btn--icon",onClick:r.onClick,"aria-label":r.label,children:_nullishCoalesce(r.icon, () => (_jsxruntime.jsx.call(void 0, ti,{})))})]})}function ei(){return _jsxruntime.jsxs.call(void 0, "svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round","aria-hidden":"true",children:[_jsxruntime.jsx.call(void 0, "line",{x1:"4",y1:"6",x2:"20",y2:"6"}),_jsxruntime.jsx.call(void 0, "circle",{cx:"9",cy:"6",r:"2",fill:"currentColor",stroke:"none"}),_jsxruntime.jsx.call(void 0, "line",{x1:"4",y1:"12",x2:"20",y2:"12"}),_jsxruntime.jsx.call(void 0, "circle",{cx:"15",cy:"12",r:"2",fill:"currentColor",stroke:"none"}),_jsxruntime.jsx.call(void 0, "line",{x1:"4",y1:"18",x2:"20",y2:"18"}),_jsxruntime.jsx.call(void 0, "circle",{cx:"11",cy:"18",r:"2",fill:"currentColor",stroke:"none"})]})}function ti(){return _jsxruntime.jsxs.call(void 0, "svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round","aria-hidden":"true",children:[_jsxruntime.jsx.call(void 0, "line",{x1:"12",y1:"5",x2:"12",y2:"19"}),_jsxruntime.jsx.call(void 0, "line",{x1:"5",y1:"12",x2:"19",y2:"12"})]})}var ii=_jsxruntime.jsx.call(void 0, "div",{className:"rle-empty",children:"Map unavailable"});function ri(){let t=_react.useRef.call(void 0, null),[e,i]=_react.useState.call(void 0, !0),[r,n]=_react.useState.call(void 0, !0);return _react.useEffect.call(void 0, ()=>{let s=t.current;if(!s)return;let o=()=>{let{clientWidth:L,scrollLeft:g,scrollWidth:P}=s;i(g<=0),n(g+L>=P-1)},l=0,d=()=>{l||(l=requestAnimationFrame(()=>{l=0,o()}))};o(),s.addEventListener("scroll",o,{passive:!0});let c,a;return typeof ResizeObserver<"u"&&(c=new ResizeObserver(o),c.observe(s)),typeof MutationObserver<"u"&&(a=new MutationObserver(d),a.observe(s,{characterData:!0,childList:!0,subtree:!0})),()=>{s.removeEventListener("scroll",o),_optionalChain([c, 'optionalAccess', _30 => _30.disconnect, 'call', _31 => _31()]),_optionalChain([a, 'optionalAccess', _32 => _32.disconnect, 'call', _33 => _33()]),l&&cancelAnimationFrame(l)}},[]),{atEnd:r,atStart:e,ref:t}}function ni(t,e){if(t===e)return!0;if(typeof t!="object"||t===null||typeof e!="object"||e===null)return!1;let i=t,r=e,n=new Set([...Object.keys(i),...Object.keys(r)]);for(let s of n)if(i[s]!==r[s])return!1;return!0}function lt({search:t,toolbarEnd:e,mobileAction:i,autoFetch:r=!0,hasMap:n,mapCenter:s,mapZoom:o,mapControls:l,mobileSheetFooter:d,className:c}){let a=y(),{Search:L}=F(),g=U(),{filters:P,set:O}=re(),{pagination:p}=C(),R=_nullishCoalesce(n, () => (a.map!=null)),[b,$]=_react.useState.call(void 0, "list"),[I,E]=_react.useState.call(void 0, !1),{atEnd:G,atStart:Z,ref:T}=ri(),[f,u]=_react.useState.call(void 0, P),[v,x]=_react.useState.call(void 0, I);I!==v&&(x(I),I&&u(P));let H=pe=>u(ct=>({...ct,...pe})),[S,Ie]=_react.useState.call(void 0, !1),de=_react.useRef.call(void 0, !1);_react.useEffect.call(void 0, ()=>{if(S){if(p.loading){de.current=!0;return}de.current&&(de.current=!1,Ie(!1),E(!1))}},[S,p.loading]);let W=t?{value:String(_nullishCoalesce(P[t.filterKey], () => (""))),onChange:pe=>{O({[t.filterKey]:pe||void 0})},placeholder:t.placeholder}:void 0;_react.useEffect.call(void 0, ()=>{r!==!1&&a.applyFilters({})},[a,r]);let Ee=()=>{H(a.filters.clearedParams())},xe=()=>{if(ni(f,P)){E(!1);return}Ie(!0),a.applyFilters(f)},pt=a.filters.activeKeys(P).length,Ne=_nullishCoalesce(g.total, () => (g.items.length));return _jsxruntime.jsxs.call(void 0, "div",{className:c?`rle-app ${c}`:"rle-app",children:[_jsxruntime.jsxs.call(void 0, "div",{className:"rle-filter-bar",children:[_jsxruntime.jsxs.call(void 0, "div",{className:"rle-filter-bar__scroll",ref:T,children:[W&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-filter-bar__search",children:_jsxruntime.jsx.call(void 0, L,{value:W.value,onChange:W.onChange,placeholder:W.placeholder})}),_jsxruntime.jsx.call(void 0, ue,{className:"rle-filters-row",groupClassName:"rle-filter-group",hideLabels:!0})]}),!Z&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-filter-bar__fade rle-filter-bar__fade--start","aria-hidden":"true"}),!G&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-filter-bar__fade rle-filter-bar__fade--end","aria-hidden":"true"})]}),_jsxruntime.jsx.call(void 0, ot,{search:W,onFiltersClick:()=>E(!0),filterCount:pt,action:i}),_jsxruntime.jsxs.call(void 0, "div",{className:`rle-body ${R?"rle-split":"rle-body--list-only"}`,"data-mobile-view":b,children:[_jsxruntime.jsxs.call(void 0, "div",{className:"rle-list",children:[_jsxruntime.jsxs.call(void 0, "div",{className:"rle-list-header",children:[_jsxruntime.jsx.call(void 0, Ze,{}),e&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-list-header__toolbar",children:e})]}),_jsxruntime.jsx.call(void 0, Ve,{className:"rle-list-grid"}),_jsxruntime.jsx.call(void 0, Ge,{})]}),R&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-map",children:_jsxruntime.jsx.call(void 0, Qe,{center:s,zoom:o,fallback:ii,mapControls:l})})]}),R&&_jsxruntime.jsx.call(void 0, rt,{view:b,onViewChange:$}),_jsxruntime.jsx.call(void 0, st,{title:"Filters",open:I,onOpenChange:E,footer:d?d({draft:f,apply:xe,clear:Ee,resultCount:Ne,loading:p.loading}):_jsxruntime.jsxs.call(void 0, _jsxruntime.Fragment,{children:[_jsxruntime.jsx.call(void 0, "button",{type:"button",className:"rle-btn rle-btn--ghost",onClick:Ee,children:"Clear all"}),_jsxruntime.jsx.call(void 0, "button",{type:"button",className:"rle-btn rle-btn--primary rle-sheet__apply",disabled:p.loading,onClick:xe,children:p.loading?_jsxruntime.jsx.call(void 0, "span",{className:"rle-spinner","aria-label":"Updating results"}):`Show ${Ne} results`})]}),children:_jsxruntime.jsx.call(void 0, ue,{className:"rle-filter-stack",groupClassName:"rle-filter-group",draft:f,onDraftChange:H})})]})}function dt(t){return"provider"in t}function di(t){let e=t!=null&&!dt(t),i=e?t.apiKey:void 0,r=e?t.mapId:void 0,n=e?t.mapOptions:void 0,s=e?t.styles:void 0,[o,l]=_react.useState.call(void 0, ()=>!t||dt(t)?{ready:!0,provider:_optionalChain([t, 'optionalAccess', _34 => _34.provider])}:{ready:!1});return _react.useEffect.call(void 0, ()=>{if(!i)return;let d=!1;return Promise.resolve().then(() => _interopRequireWildcard(require("./maps/google/index.cjs"))).then(({googleProvider:c})=>{d||l({ready:!0,provider:c({apiKey:i,mapId:r,mapOptions:n,styles:s})})}),()=>{d=!0}},[i,r]),o}function pi({onFiltersChange:t}){let e=_react.useRef.call(void 0, t);return e.current=t,Xe("FiltersChanged",i=>{i.type==="FiltersChanged"&&e.current(i.filters)}),null}function Nn(t){let{datasets:e,filters:i,map:r,components:n,initialFilters:s,onFiltersChange:o,mobileAction:l,search:d,toolbarEnd:c,mapControls:a,mobileSheetFooter:L,config:g,autoFetch:P,className:O}=t,{ready:p,provider:R}=di(r);if(!p)return null;let b=[];for(let E of e)b.push(_e(E));i&&b.push(Be(i)),R&&b.push(Oe(R)),s&&b.push(Ae(s)),g&&b.push(De(g));let $=Me(...b),I={...it,...n};return _jsxruntime.jsxs.call(void 0, Ye,{...$,children:[o&&_jsxruntime.jsx.call(void 0, pi,{onFiltersChange:o}),_jsxruntime.jsx.call(void 0, ze,{...I,children:_jsxruntime.jsx.call(void 0, lt,{className:O,search:d,toolbarEnd:c,mobileAction:l,autoFetch:P,mapCenter:_optionalChain([r, 'optionalAccess', _35 => _35.center]),mapZoom:_optionalChain([r, 'optionalAccess', _36 => _36.zoom]),mapControls:a,mobileSheetFooter:L})})]})}exports.a = X; exports.b = z; exports.c = J; exports.d = Y; exports.e = Re; exports.f = ee; exports.g = te; exports.h = Me; exports.i = De; exports.j = Oe; exports.k = _e; exports.l = Be; exports.m = Si; exports.n = Ae; exports.o = ki; exports.p = ce; exports.q = ze; exports.r = F; exports.s = ie; exports.t = y; exports.u = C; exports.v = re; exports.w = ue; exports.x = U; exports.y = Ve; exports.z = Qe; exports.A = Ge; exports.B = Ze; exports.C = Xe; exports.D = Ye; exports.E = fe; exports.F = ge; exports.G = ye; exports.H = ve; exports.I = he; exports.J = be; exports.K = Te; exports.L = Pe; exports.M = Fe; exports.N = Ce; exports.O = it; exports.P = rt; exports.Q = st; exports.R = lt; exports.S = Nn;
|
package/dist/index.cjs
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
1
|
"use strict";Object.defineProperty(exports, "__esModule", {value: true}); function _nullishCoalesce(lhs, rhsFn) { if (lhs != null) { return lhs; } else { return rhsFn(); } } function _optionalChain(ops) { let lastAccessLHS = undefined; let value = ops[0]; let i = 1; while (i < ops.length) { const op = ops[i]; const fn = ops[i + 1]; i += 2; if ((op === 'optionalAccess' || op === 'optionalCall') && value == null) { return undefined; } if (op === 'access' || op === 'optionalAccess') { lastAccessLHS = value; value = fn(value); } else if (op === 'call' || op === 'optionalCall') { value = fn((...args) => value.call(lastAccessLHS, ...args)); lastAccessLHS = undefined; } } return value; } var _class; var _class2;"use client";
|
|
2
|
-
var
|
|
2
|
+
var _chunkHTNCZ5NScjs = require('./chunk-HTNCZ5NS.cjs');var P=(r=>(r.Paged="paged",r.Infinite="infinite",r))(P||{});var b=(s=>(s.FiltersChanged="FiltersChanged",s.ResultsLoaded="ResultsLoaded",s.PointClicked="PointClicked",s.BoundsChanged="BoundsChanged",s.LayerToggled="LayerToggled",s))(b||{});var d= (_class =class{__init() {this.listeners=new Set}constructor(t={}){;_class.prototype.__init.call(this);this.query={...t}}getQuery(){return{...this.query}}setQuery(t){this.query={...t},this.notify()}subscribe(t){return this.listeners.add(t),()=>{this.listeners.delete(t)}}notify(){for(let t of[...this.listeners])t()}}, _class);function v(e,t){let r=new Set([...Object.keys(e),...Object.keys(t)]);for(let i of r)if(e[i]!==t[i])return!1;return!0}var h= (_class2 =class{__init2() {this.isSyncing=!1}__init3() {this.unsubscribeEngine=null}__init4() {this.unsubscribeHistory=null}constructor(t){;_class2.prototype.__init2.call(this);_class2.prototype.__init3.call(this);_class2.prototype.__init4.call(this);this.history=t.history,this.toQueryFn=t.toQuery,this.toFiltersFn=t.toFilters,this.hydrateOnStart=_nullishCoalesce(t.hydrateOnStart, () => (!0))}start(t){this.stop(),this.unsubscribeEngine=t.subscribe(()=>{this.isSyncing||this.syncEngineToHistory(t)}),this.unsubscribeHistory=this.history.subscribe(()=>{this.isSyncing||this.withSyncGuard(()=>{this.applyFiltersSafely(t,this.toFiltersFn(this.history.getQuery()))})}),this.hydrateOnStart&&this.withSyncGuard(()=>{this.applyFiltersSafely(t,this.toFiltersFn(this.history.getQuery()))})}stop(){_optionalChain([this, 'access', _ => _.unsubscribeEngine, 'optionalCall', _2 => _2()]),this.unsubscribeEngine=null,_optionalChain([this, 'access', _3 => _3.unsubscribeHistory, 'optionalCall', _4 => _4()]),this.unsubscribeHistory=null}syncEngineToHistory(t){let r=this.toQueryFn(t.state.filters);v(r,this.history.getQuery())||this.withSyncGuard(()=>this.history.setQuery(r))}applyFiltersSafely(t,r){Promise.resolve(t.applyFilters(r)).catch(()=>{})}withSyncGuard(t){this.isSyncing=!0;try{t()}finally{this.isSyncing=!1}}}, _class2);var m=class{constructor(t={}){this.mode=_nullishCoalesce(t.mode, () => ("replace"))}getQuery(){if(typeof window>"u")return{};let t=new URLSearchParams(window.location.search),r={};for(let[i,o]of t)o!==""&&(r[i]=o);return r}setQuery(t){if(typeof window>"u")return;let r=new URLSearchParams;for(let[c,a]of Object.entries(t))a===void 0||a===""||r.set(c,a);let i=r.toString(),o=i?`?${i}`:"";if(o===window.location.search)return;let s=`${window.location.pathname}${o}${window.location.hash}`;this.mode==="push"?window.history.pushState(window.history.state,"",s):window.history.replaceState(window.history.state,"",s)}subscribe(t){return typeof window>"u"?()=>{}:(window.addEventListener("popstate",t),()=>{window.removeEventListener("popstate",t)})}};var _jsxruntime = require('react/jsx-runtime');function rt({children:e}){let{Toolbar:t}=_chunkHTNCZ5NScjs.r.call(void 0, );return _jsxruntime.jsx.call(void 0, t,{children:e})}var _react = require('react');function lt(){let e=_chunkHTNCZ5NScjs.t.call(void 0, ),t=_chunkHTNCZ5NScjs.u.call(void 0, ),r=_react.useCallback.call(void 0, l=>e.loadPoints(l),[e]),i=_react.useCallback.call(void 0, (l,f)=>e.selectPoint(l,f),[e]),o=_react.useCallback.call(void 0, l=>e.setHovered(e.primaryDatasetId,l),[e]),s=_react.useCallback.call(void 0, ()=>_optionalChain([e, 'access', _5 => _5.map, 'optionalAccess', _6 => _6.zoomIn, 'call', _7 => _7()]),[e]),c=_react.useCallback.call(void 0, ()=>_optionalChain([e, 'access', _8 => _8.map, 'optionalAccess', _9 => _9.zoomOut, 'call', _10 => _10()]),[e]),a=_react.useCallback.call(void 0, ()=>_optionalChain([e, 'access', _11 => _11.map, 'optionalAccess', _12 => _12.toggleFullscreen, 'call', _13 => _13()]),[e]);return{bounds:t.bounds,points:t.points,hovered:t.hovered,loadPoints:r,selectPoint:i,setHovered:o,zoomIn:s,zoomOut:c,toggleFullscreen:a}}function dt(e){let t=_chunkHTNCZ5NScjs.t.call(void 0, ),r=_chunkHTNCZ5NScjs.u.call(void 0, ),i=_react.useCallback.call(void 0, ()=>t.toggleLayer(e),[t,e]);return{visible:_nullishCoalesce(r.layers[e], () => (!0)),points:_nullishCoalesce(r.points[e], () => ([])),toggle:i}}exports.BrowserHistoryPort = m; exports.DatasetRegistry = _chunkHTNCZ5NScjs.c; exports.FallbackPopup = _chunkHTNCZ5NScjs.p; exports.FilterRegistry = _chunkHTNCZ5NScjs.b; exports.ListingApp = _chunkHTNCZ5NScjs.S; exports.ListingComponentsProvider = _chunkHTNCZ5NScjs.q; exports.ListingConfig = _chunkHTNCZ5NScjs.f; exports.ListingEngine = _chunkHTNCZ5NScjs.g; exports.ListingEngineContext = _chunkHTNCZ5NScjs.s; exports.ListingEventType = b; exports.ListingFilters = _chunkHTNCZ5NScjs.w; exports.ListingList = _chunkHTNCZ5NScjs.y; exports.ListingMap = _chunkHTNCZ5NScjs.z; exports.ListingPagination = _chunkHTNCZ5NScjs.A; exports.ListingProvider = _chunkHTNCZ5NScjs.D; exports.ListingResultHeader = _chunkHTNCZ5NScjs.B; exports.ListingStore = _chunkHTNCZ5NScjs.a; exports.ListingToolbar = rt; exports.MemoryHistoryPort = d; exports.PaginationMode = P; exports.TypedEmitter = _chunkHTNCZ5NScjs.d; exports.UrlSyncController = h; exports.composeListingProviders = _chunkHTNCZ5NScjs.h; exports.listingDefaultConfig = _chunkHTNCZ5NScjs.e; exports.useListing = _chunkHTNCZ5NScjs.t; exports.useListingComponents = _chunkHTNCZ5NScjs.r; exports.useListingEvent = _chunkHTNCZ5NScjs.C; exports.useListingFilters = _chunkHTNCZ5NScjs.v; exports.useListingLayer = dt; exports.useListingMap = lt; exports.useListingResults = _chunkHTNCZ5NScjs.x; exports.useListingState = _chunkHTNCZ5NScjs.u; exports.withConfig = _chunkHTNCZ5NScjs.i; exports.withDataset = _chunkHTNCZ5NScjs.k; exports.withFilters = _chunkHTNCZ5NScjs.l; exports.withInitialFilters = _chunkHTNCZ5NScjs.n; exports.withMap = _chunkHTNCZ5NScjs.j; exports.withPrimaryDataset = _chunkHTNCZ5NScjs.o; exports.withUrlSync = _chunkHTNCZ5NScjs.m;
|
package/dist/index.d.cts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { P as Page, B as Bounds, E as EntityId, M as MapPoint, U as Unsubscribe, a as MapProvider, Q as QueryParams, L as LatLng } from './map-provider.interface-B5Law7gE.cjs';
|
|
2
2
|
export { b as EntityAdapter, c as MapHandle, d as MapInitOptions, e as MapOverlayHandle, f as PageRequest, R as RenderedLayer } from './map-provider.interface-B5Law7gE.cjs';
|
|
3
|
-
import { P as PaginationMode, D as DatasetDefinition, I as IListingConfigOptions, F as FilterRegistry, a as IListingToolbarProps } from './listing-app-
|
|
4
|
-
export { C as ClusterOptions, b as FallbackPopup, c as FilterControlProps, d as FilterDefinition, e as IListingCardProps, f as IListingComponents, g as IListingEmptyProps, h as IListingFilterPanelProps, i as IListingLoadingProps, j as IListingMarkerProps, k as IListingPopupProps, l as IListingResultHeaderProps, m as IListingSearchProps, n as IListingSidebarProps, L as ListingApp, o as ListingAppProps, p as ListingComponentsProvider, M as MarkerRenderer, u as useListingComponents } from './listing-app-
|
|
3
|
+
import { P as PaginationMode, D as DatasetDefinition, I as IListingConfigOptions, F as FilterRegistry, a as IListingToolbarProps } from './listing-app-BKE75k--.cjs';
|
|
4
|
+
export { C as ClusterOptions, b as FallbackPopup, c as FilterControlProps, d as FilterDefinition, e as IListingCardProps, f as IListingComponents, g as IListingEmptyProps, h as IListingFilterPanelProps, i as IListingLoadingProps, j as IListingMarkerProps, k as IListingPopupProps, l as IListingResultHeaderProps, m as IListingSearchProps, n as IListingSidebarProps, L as ListingApp, o as ListingAppProps, p as ListingComponentsProvider, M as MarkerRenderer, q as MobileSheetFooterContext, u as useListingComponents } from './listing-app-BKE75k--.cjs';
|
|
5
5
|
import * as react from 'react';
|
|
6
6
|
import { ReactNode } from 'react';
|
|
7
7
|
|
|
@@ -376,7 +376,7 @@ declare class BrowserHistoryPort implements HistoryPort {
|
|
|
376
376
|
subscribe(cb: () => void): () => void;
|
|
377
377
|
}
|
|
378
378
|
|
|
379
|
-
interface IListingFiltersProps {
|
|
379
|
+
interface IListingFiltersProps<TFilters = unknown> {
|
|
380
380
|
/**
|
|
381
381
|
* ClassName for the container wrapping every filter group. Purely a
|
|
382
382
|
* styling hook -- this component stays structure-only, so it never bakes
|
|
@@ -394,6 +394,24 @@ interface IListingFiltersProps {
|
|
|
394
394
|
* leave off (labels shown) for a stacked form layout like the mobile sheet.
|
|
395
395
|
*/
|
|
396
396
|
hideLabels?: boolean;
|
|
397
|
+
/**
|
|
398
|
+
* Deferred/draft mode: supply alongside `onDraftChange` to have every
|
|
399
|
+
* control read its value from `def.fromParams(draft)` instead of the
|
|
400
|
+
* engine's live applied filters, and route `onChange` through
|
|
401
|
+
* `onDraftChange` instead of `engine.applyFilters`. Nothing reaches the
|
|
402
|
+
* engine until the caller applies its own accumulated draft (e.g. the
|
|
403
|
+
* mobile sheet's "Show N results" button committing it via
|
|
404
|
+
* `engine.applyFilters(draft)`).
|
|
405
|
+
*
|
|
406
|
+
* Both `draft` and `onDraftChange` must be supplied together to enable
|
|
407
|
+
* deferred mode -- either one alone falls back to the original LIVE
|
|
408
|
+
* behavior (default, used by the desktop filter bar): each control reads
|
|
409
|
+
* `engine.filters`/live applied state and applies straight to the engine
|
|
410
|
+
* on change.
|
|
411
|
+
*/
|
|
412
|
+
draft?: TFilters;
|
|
413
|
+
/** Paired with `draft` to enable deferred mode -- see `draft`'s doc. */
|
|
414
|
+
onDraftChange?: (params: Partial<TFilters>) => void;
|
|
397
415
|
}
|
|
398
416
|
/**
|
|
399
417
|
* Structure-only filter panel: one control per `engine.filters.list()` entry,
|
|
@@ -422,8 +440,14 @@ interface IListingFiltersProps {
|
|
|
422
440
|
* behavior). Passing a horizontal `className` does NOT change the
|
|
423
441
|
* label-above-control structure within each group -- only how the groups
|
|
424
442
|
* themselves are laid out relative to each other.
|
|
443
|
+
*
|
|
444
|
+
* `draft`/`onDraftChange` (both required together) switch every control from
|
|
445
|
+
* LIVE (read/write straight through `engine.filters`/`applyFilters`) to
|
|
446
|
+
* DEFERRED (read/write through the caller's own draft state) -- see
|
|
447
|
+
* `IListingFiltersProps.draft`'s doc. Omitted (the default), this component's
|
|
448
|
+
* behavior is unchanged from before either prop existed.
|
|
425
449
|
*/
|
|
426
|
-
declare function ListingFilters({ className, groupClassName, hideLabels }?: IListingFiltersProps): react.JSX.Element;
|
|
450
|
+
declare function ListingFilters<TFilters = unknown>({ className, groupClassName, hideLabels, draft, onDraftChange, }?: IListingFiltersProps<TFilters>): react.JSX.Element;
|
|
427
451
|
|
|
428
452
|
/**
|
|
429
453
|
* Structure-only results list. Renders the injected `Loading` while the
|
package/dist/index.d.ts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { P as Page, B as Bounds, E as EntityId, M as MapPoint, U as Unsubscribe, a as MapProvider, Q as QueryParams, L as LatLng } from './map-provider.interface-B5Law7gE.js';
|
|
2
2
|
export { b as EntityAdapter, c as MapHandle, d as MapInitOptions, e as MapOverlayHandle, f as PageRequest, R as RenderedLayer } from './map-provider.interface-B5Law7gE.js';
|
|
3
|
-
import { P as PaginationMode, D as DatasetDefinition, I as IListingConfigOptions, F as FilterRegistry, a as IListingToolbarProps } from './listing-app-
|
|
4
|
-
export { C as ClusterOptions, b as FallbackPopup, c as FilterControlProps, d as FilterDefinition, e as IListingCardProps, f as IListingComponents, g as IListingEmptyProps, h as IListingFilterPanelProps, i as IListingLoadingProps, j as IListingMarkerProps, k as IListingPopupProps, l as IListingResultHeaderProps, m as IListingSearchProps, n as IListingSidebarProps, L as ListingApp, o as ListingAppProps, p as ListingComponentsProvider, M as MarkerRenderer, u as useListingComponents } from './listing-app-
|
|
3
|
+
import { P as PaginationMode, D as DatasetDefinition, I as IListingConfigOptions, F as FilterRegistry, a as IListingToolbarProps } from './listing-app-CRGXBErM.js';
|
|
4
|
+
export { C as ClusterOptions, b as FallbackPopup, c as FilterControlProps, d as FilterDefinition, e as IListingCardProps, f as IListingComponents, g as IListingEmptyProps, h as IListingFilterPanelProps, i as IListingLoadingProps, j as IListingMarkerProps, k as IListingPopupProps, l as IListingResultHeaderProps, m as IListingSearchProps, n as IListingSidebarProps, L as ListingApp, o as ListingAppProps, p as ListingComponentsProvider, M as MarkerRenderer, q as MobileSheetFooterContext, u as useListingComponents } from './listing-app-CRGXBErM.js';
|
|
5
5
|
import * as react from 'react';
|
|
6
6
|
import { ReactNode } from 'react';
|
|
7
7
|
|
|
@@ -376,7 +376,7 @@ declare class BrowserHistoryPort implements HistoryPort {
|
|
|
376
376
|
subscribe(cb: () => void): () => void;
|
|
377
377
|
}
|
|
378
378
|
|
|
379
|
-
interface IListingFiltersProps {
|
|
379
|
+
interface IListingFiltersProps<TFilters = unknown> {
|
|
380
380
|
/**
|
|
381
381
|
* ClassName for the container wrapping every filter group. Purely a
|
|
382
382
|
* styling hook -- this component stays structure-only, so it never bakes
|
|
@@ -394,6 +394,24 @@ interface IListingFiltersProps {
|
|
|
394
394
|
* leave off (labels shown) for a stacked form layout like the mobile sheet.
|
|
395
395
|
*/
|
|
396
396
|
hideLabels?: boolean;
|
|
397
|
+
/**
|
|
398
|
+
* Deferred/draft mode: supply alongside `onDraftChange` to have every
|
|
399
|
+
* control read its value from `def.fromParams(draft)` instead of the
|
|
400
|
+
* engine's live applied filters, and route `onChange` through
|
|
401
|
+
* `onDraftChange` instead of `engine.applyFilters`. Nothing reaches the
|
|
402
|
+
* engine until the caller applies its own accumulated draft (e.g. the
|
|
403
|
+
* mobile sheet's "Show N results" button committing it via
|
|
404
|
+
* `engine.applyFilters(draft)`).
|
|
405
|
+
*
|
|
406
|
+
* Both `draft` and `onDraftChange` must be supplied together to enable
|
|
407
|
+
* deferred mode -- either one alone falls back to the original LIVE
|
|
408
|
+
* behavior (default, used by the desktop filter bar): each control reads
|
|
409
|
+
* `engine.filters`/live applied state and applies straight to the engine
|
|
410
|
+
* on change.
|
|
411
|
+
*/
|
|
412
|
+
draft?: TFilters;
|
|
413
|
+
/** Paired with `draft` to enable deferred mode -- see `draft`'s doc. */
|
|
414
|
+
onDraftChange?: (params: Partial<TFilters>) => void;
|
|
397
415
|
}
|
|
398
416
|
/**
|
|
399
417
|
* Structure-only filter panel: one control per `engine.filters.list()` entry,
|
|
@@ -422,8 +440,14 @@ interface IListingFiltersProps {
|
|
|
422
440
|
* behavior). Passing a horizontal `className` does NOT change the
|
|
423
441
|
* label-above-control structure within each group -- only how the groups
|
|
424
442
|
* themselves are laid out relative to each other.
|
|
443
|
+
*
|
|
444
|
+
* `draft`/`onDraftChange` (both required together) switch every control from
|
|
445
|
+
* LIVE (read/write straight through `engine.filters`/`applyFilters`) to
|
|
446
|
+
* DEFERRED (read/write through the caller's own draft state) -- see
|
|
447
|
+
* `IListingFiltersProps.draft`'s doc. Omitted (the default), this component's
|
|
448
|
+
* behavior is unchanged from before either prop existed.
|
|
425
449
|
*/
|
|
426
|
-
declare function ListingFilters({ className, groupClassName, hideLabels }?: IListingFiltersProps): react.JSX.Element;
|
|
450
|
+
declare function ListingFilters<TFilters = unknown>({ className, groupClassName, hideLabels, draft, onDraftChange, }?: IListingFiltersProps<TFilters>): react.JSX.Element;
|
|
427
451
|
|
|
428
452
|
/**
|
|
429
453
|
* Structure-only results list. Renders the injected `Loading` while the
|
package/dist/index.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
1
|
"use client";
|
|
2
|
-
import{A as N,B as V,C as W,D as X,S as g,a as S,b as Q,c as x,d as T,e as L,f as H,g as O,h as E,i as k,j as q,k as
|
|
2
|
+
import{A as N,B as V,C as W,D as X,S as g,a as S,b as Q,c as x,d as T,e as L,f as H,g as O,h as E,i as k,j as q,k as C,l as I,m as U,n as B,o as z,p as G,q as R,r as p,s as $,t as u,u as y,v as j,w as A,x as D,y as J,z as K}from"./chunk-CJQJDGBU.js";var P=(r=>(r.Paged="paged",r.Infinite="infinite",r))(P||{});var b=(s=>(s.FiltersChanged="FiltersChanged",s.ResultsLoaded="ResultsLoaded",s.PointClicked="PointClicked",s.BoundsChanged="BoundsChanged",s.LayerToggled="LayerToggled",s))(b||{});var d=class{query;listeners=new Set;constructor(t={}){this.query={...t}}getQuery(){return{...this.query}}setQuery(t){this.query={...t},this.notify()}subscribe(t){return this.listeners.add(t),()=>{this.listeners.delete(t)}}notify(){for(let t of[...this.listeners])t()}};function v(e,t){let r=new Set([...Object.keys(e),...Object.keys(t)]);for(let i of r)if(e[i]!==t[i])return!1;return!0}var h=class{history;toQueryFn;toFiltersFn;hydrateOnStart;isSyncing=!1;unsubscribeEngine=null;unsubscribeHistory=null;constructor(t){this.history=t.history,this.toQueryFn=t.toQuery,this.toFiltersFn=t.toFilters,this.hydrateOnStart=t.hydrateOnStart??!0}start(t){this.stop(),this.unsubscribeEngine=t.subscribe(()=>{this.isSyncing||this.syncEngineToHistory(t)}),this.unsubscribeHistory=this.history.subscribe(()=>{this.isSyncing||this.withSyncGuard(()=>{this.applyFiltersSafely(t,this.toFiltersFn(this.history.getQuery()))})}),this.hydrateOnStart&&this.withSyncGuard(()=>{this.applyFiltersSafely(t,this.toFiltersFn(this.history.getQuery()))})}stop(){this.unsubscribeEngine?.(),this.unsubscribeEngine=null,this.unsubscribeHistory?.(),this.unsubscribeHistory=null}syncEngineToHistory(t){let r=this.toQueryFn(t.state.filters);v(r,this.history.getQuery())||this.withSyncGuard(()=>this.history.setQuery(r))}applyFiltersSafely(t,r){Promise.resolve(t.applyFilters(r)).catch(()=>{})}withSyncGuard(t){this.isSyncing=!0;try{t()}finally{this.isSyncing=!1}}};var m=class{mode;constructor(t={}){this.mode=t.mode??"replace"}getQuery(){if(typeof window>"u")return{};let t=new URLSearchParams(window.location.search),r={};for(let[i,o]of t)o!==""&&(r[i]=o);return r}setQuery(t){if(typeof window>"u")return;let r=new URLSearchParams;for(let[c,a]of Object.entries(t))a===void 0||a===""||r.set(c,a);let i=r.toString(),o=i?`?${i}`:"";if(o===window.location.search)return;let s=`${window.location.pathname}${o}${window.location.hash}`;this.mode==="push"?window.history.pushState(window.history.state,"",s):window.history.replaceState(window.history.state,"",s)}subscribe(t){return typeof window>"u"?()=>{}:(window.addEventListener("popstate",t),()=>{window.removeEventListener("popstate",t)})}};import{jsx as F}from"react/jsx-runtime";function rt({children:e}){let{Toolbar:t}=p();return F(t,{children:e})}import{useCallback as n}from"react";function lt(){let e=u(),t=y(),r=n(l=>e.loadPoints(l),[e]),i=n((l,f)=>e.selectPoint(l,f),[e]),o=n(l=>e.setHovered(e.primaryDatasetId,l),[e]),s=n(()=>e.map?.zoomIn(),[e]),c=n(()=>e.map?.zoomOut(),[e]),a=n(()=>e.map?.toggleFullscreen(),[e]);return{bounds:t.bounds,points:t.points,hovered:t.hovered,loadPoints:r,selectPoint:i,setHovered:o,zoomIn:s,zoomOut:c,toggleFullscreen:a}}import{useCallback as w}from"react";function dt(e){let t=u(),r=y(),i=w(()=>t.toggleLayer(e),[t,e]);return{visible:r.layers[e]??!0,points:r.points[e]??[],toggle:i}}export{m as BrowserHistoryPort,x as DatasetRegistry,G as FallbackPopup,Q as FilterRegistry,g as ListingApp,R as ListingComponentsProvider,H as ListingConfig,O as ListingEngine,$ as ListingEngineContext,b as ListingEventType,A as ListingFilters,J as ListingList,K as ListingMap,N as ListingPagination,X as ListingProvider,V as ListingResultHeader,S as ListingStore,rt as ListingToolbar,d as MemoryHistoryPort,P as PaginationMode,T as TypedEmitter,h as UrlSyncController,E as composeListingProviders,L as listingDefaultConfig,u as useListing,p as useListingComponents,W as useListingEvent,j as useListingFilters,dt as useListingLayer,lt as useListingMap,D as useListingResults,y as useListingState,k as withConfig,C as withDataset,I as withFilters,B as withInitialFilters,q as withMap,z as withPrimaryDataset,U as withUrlSync};
|
|
@@ -158,7 +158,23 @@ interface IBottomNavProps {
|
|
|
158
158
|
*/
|
|
159
159
|
declare function BottomNav({ view, onViewChange }: IBottomNavProps): react.JSX.Element;
|
|
160
160
|
|
|
161
|
-
|
|
161
|
+
/**
|
|
162
|
+
* Handed to `IStyledListingLayoutProps.mobileSheetFooter` -- see that prop's
|
|
163
|
+
* doc comment for why this render-prop override exists.
|
|
164
|
+
*/
|
|
165
|
+
interface MobileSheetFooterContext<TFilters> {
|
|
166
|
+
/** The sheet's current DRAFT filters -- buffered edits not yet applied to the engine (see the class doc's `BottomSheet` section). */
|
|
167
|
+
draft: TFilters;
|
|
168
|
+
/** Commits `draft` to the engine and closes the sheet once the resulting refetch settles -- identical to what the default "Show N results" button does (`handleApplyDraft`). */
|
|
169
|
+
apply: () => void;
|
|
170
|
+
/** Resets the DRAFT (not the applied filters) via `engine.filters.clearedParams()` -- identical to what the default "Clear all" button does (`handleClearAll`). */
|
|
171
|
+
clear: () => void;
|
|
172
|
+
/** The currently APPLIED result count -- NOT a live preview of `draft` (see `mobileSheetFooter`'s doc comment for why). */
|
|
173
|
+
resultCount: number;
|
|
174
|
+
/** `pagination.loading` -- true while a commit-triggered (or any other) refetch is in flight. */
|
|
175
|
+
loading: boolean;
|
|
176
|
+
}
|
|
177
|
+
interface IStyledListingLayoutProps<TFilters = unknown> {
|
|
162
178
|
/**
|
|
163
179
|
* Optional header search box, LIBRARY-wired: name the `TFilters` field it
|
|
164
180
|
* drives via
|
|
@@ -192,6 +208,21 @@ interface IStyledListingLayoutProps {
|
|
|
192
208
|
mapZoom?: number;
|
|
193
209
|
/** Forwarded verbatim to `<ListingMap mapControls={mapControls} />` -- see that prop's doc comment. */
|
|
194
210
|
mapControls?: ReactNode;
|
|
211
|
+
/**
|
|
212
|
+
* Render-prop override for the mobile filters sheet's footer -- when
|
|
213
|
+
* given, replaces the default "Clear all" + "Show N results" buttons
|
|
214
|
+
* entirely, called with the sheet's current draft plus its
|
|
215
|
+
* commit/clear/count/loading state (see `MobileSheetFooterContext`'s own
|
|
216
|
+
* field docs). Exists because the default footer's result count is always
|
|
217
|
+
* the currently APPLIED count (see the class doc's `BottomSheet` section)
|
|
218
|
+
* -- it never previews what applying `draft` WOULD return, since that
|
|
219
|
+
* requires a query only the consumer's own data source can run (e.g. a
|
|
220
|
+
* live-count endpoint keyed off the draft). A consumer with such a source
|
|
221
|
+
* renders its own footer here, driving `apply`/`clear` exactly like the
|
|
222
|
+
* default buttons do. Omitted (the default), the built-in footer renders
|
|
223
|
+
* unchanged.
|
|
224
|
+
*/
|
|
225
|
+
mobileSheetFooter?: (ctx: MobileSheetFooterContext<TFilters>) => ReactNode;
|
|
195
226
|
className?: string;
|
|
196
227
|
}
|
|
197
228
|
/**
|
|
@@ -228,17 +259,36 @@ interface IStyledListingLayoutProps {
|
|
|
228
259
|
* the same `mobileView` state as the CSS toggle. Omitted when there is no
|
|
229
260
|
* map (nothing to toggle to).
|
|
230
261
|
* - `<BottomSheet title="Filters">`: the SAME `<ListingFilters>` component,
|
|
231
|
-
* stacked vertically (`className="rle-filter-stack"`)
|
|
232
|
-
*
|
|
262
|
+
* stacked vertically (`className="rle-filter-stack"`), but in DEFERRED mode
|
|
263
|
+
* (`draft`/`onDraftChange` -- see that component's doc): every control edit
|
|
264
|
+
* inside the sheet buffers into local `draft` state instead of applying to
|
|
265
|
+
* the engine, so the list/map behind the sheet never move while it's open.
|
|
266
|
+
* `draft` is re-synced from the currently applied filters each time the
|
|
267
|
+
* sheet transitions closed -> open (a render-phase adjustment, not an
|
|
268
|
+
* effect). The footer has "Clear all" (resets the DRAFT via
|
|
233
269
|
* `engine.filters.clearedParams()` -- see that method's doc for why a reset
|
|
234
|
-
* round-trips each def's to/fromParams
|
|
235
|
-
*
|
|
236
|
-
*
|
|
270
|
+
* round-trips each def's to/fromParams -- NOT applied until committed) and
|
|
271
|
+
* "Show N results", which commits: `engine.applyFilters(draft)`, then
|
|
272
|
+
* closes the sheet once the resulting refetch settles (or immediately, with
|
|
273
|
+
* no refetch at all, if the draft is unchanged from what's already
|
|
274
|
+
* applied -- see `handleApplyDraft`). While a commit's refetch (or any
|
|
275
|
+
* OTHER live refetch, e.g. the desktop bar or search box, which still apply
|
|
276
|
+
* immediately) is in flight -- `pagination.loading` (`useListingState()`) is
|
|
277
|
+
* true -- the apply button is `disabled` and its label swaps for a
|
|
278
|
+
* `.rle-spinner`, so the sheet reads as "updating" instead of letting the
|
|
279
|
+
* user close onto a stale count. `.rle-sheet__apply` pins a `min-width` so
|
|
280
|
+
* that swap never changes the button's footprint. The result count itself
|
|
281
|
+
* (`Show N results`) always reflects the currently APPLIED results, not a
|
|
282
|
+
* live preview of the draft -- it only changes once a commit lands. A
|
|
283
|
+
* consumer needing a live preview (e.g. its own count endpoint keyed off
|
|
284
|
+
* the draft) can replace this whole footer via the `mobileSheetFooter`
|
|
285
|
+
* render prop -- see `IStyledListingLayoutProps.mobileSheetFooter`'s doc
|
|
286
|
+
* comment; omitted (the default), the footer above renders unchanged.
|
|
237
287
|
* - Fetches the first page itself on mount (`engine.applyFilters({})`) by
|
|
238
288
|
* default -- pass `autoFetch={false}`
|
|
239
289
|
* to opt out and drive the first fetch yourself.
|
|
240
290
|
*/
|
|
241
|
-
declare function StyledListingLayout({ search, toolbarEnd, mobileAction, autoFetch, hasMap: hasMapProp, mapCenter, mapZoom, mapControls, className, }: IStyledListingLayoutProps): react.JSX.Element;
|
|
291
|
+
declare function StyledListingLayout<TFilters = unknown>({ search, toolbarEnd, mobileAction, autoFetch, hasMap: hasMapProp, mapCenter, mapZoom, mapControls, mobileSheetFooter, className, }: IStyledListingLayoutProps<TFilters>): react.JSX.Element;
|
|
242
292
|
|
|
243
293
|
/**
|
|
244
294
|
* Two-shape `map` prop: pass a ready `MapProvider`, or the `{ apiKey, mapId? }`
|
|
@@ -320,6 +370,8 @@ interface ListingAppProps<TFilters> {
|
|
|
320
370
|
* drops the map region entirely in that case).
|
|
321
371
|
*/
|
|
322
372
|
mapControls?: ReactNode;
|
|
373
|
+
/** Forwarded verbatim to `StyledListingLayout`'s `mobileSheetFooter` -- see that prop's doc comment. */
|
|
374
|
+
mobileSheetFooter?: (ctx: MobileSheetFooterContext<TFilters>) => ReactNode;
|
|
323
375
|
config?: Partial<IListingConfigOptions>;
|
|
324
376
|
autoFetch?: boolean;
|
|
325
377
|
className?: string;
|
|
@@ -359,4 +411,4 @@ interface ListingAppProps<TFilters> {
|
|
|
359
411
|
*/
|
|
360
412
|
declare function ListingApp<TEntity, TFilters>(props: ListingAppProps<TFilters>): react.JSX.Element | null;
|
|
361
413
|
|
|
362
|
-
export { BottomNav as B, type ClusterOptions as C, type DatasetDefinition as D, FilterRegistry as F, type IListingConfigOptions as I, ListingApp as L, type MarkerRenderer as M, PaginationMode as P, StyledListingLayout as S, type IListingToolbarProps as a, FallbackPopup as b, type FilterControlProps as c, type FilterDefinition as d, type IListingCardProps as e, type IListingComponents as f, type IListingEmptyProps as g, type IListingFilterPanelProps as h, type IListingLoadingProps as i, type IListingMarkerProps as j, type IListingPopupProps as k, type IListingResultHeaderProps as l, type IListingSearchProps as m, type IListingSidebarProps as n, type ListingAppProps as o, ListingComponentsProvider as p, type
|
|
414
|
+
export { BottomNav as B, type ClusterOptions as C, type DatasetDefinition as D, FilterRegistry as F, type IListingConfigOptions as I, ListingApp as L, type MarkerRenderer as M, PaginationMode as P, StyledListingLayout as S, type IListingToolbarProps as a, FallbackPopup as b, type FilterControlProps as c, type FilterDefinition as d, type IListingCardProps as e, type IListingComponents as f, type IListingEmptyProps as g, type IListingFilterPanelProps as h, type IListingLoadingProps as i, type IListingMarkerProps as j, type IListingPopupProps as k, type IListingResultHeaderProps as l, type IListingSearchProps as m, type IListingSidebarProps as n, type ListingAppProps as o, ListingComponentsProvider as p, type MobileSheetFooterContext as q, type BottomNavView as r, type IBottomNavAction as s, type IBottomNavProps as t, useListingComponents as u, type IStyledListingLayoutProps as v, type ListingAppMapProp as w };
|
|
@@ -158,7 +158,23 @@ interface IBottomNavProps {
|
|
|
158
158
|
*/
|
|
159
159
|
declare function BottomNav({ view, onViewChange }: IBottomNavProps): react.JSX.Element;
|
|
160
160
|
|
|
161
|
-
|
|
161
|
+
/**
|
|
162
|
+
* Handed to `IStyledListingLayoutProps.mobileSheetFooter` -- see that prop's
|
|
163
|
+
* doc comment for why this render-prop override exists.
|
|
164
|
+
*/
|
|
165
|
+
interface MobileSheetFooterContext<TFilters> {
|
|
166
|
+
/** The sheet's current DRAFT filters -- buffered edits not yet applied to the engine (see the class doc's `BottomSheet` section). */
|
|
167
|
+
draft: TFilters;
|
|
168
|
+
/** Commits `draft` to the engine and closes the sheet once the resulting refetch settles -- identical to what the default "Show N results" button does (`handleApplyDraft`). */
|
|
169
|
+
apply: () => void;
|
|
170
|
+
/** Resets the DRAFT (not the applied filters) via `engine.filters.clearedParams()` -- identical to what the default "Clear all" button does (`handleClearAll`). */
|
|
171
|
+
clear: () => void;
|
|
172
|
+
/** The currently APPLIED result count -- NOT a live preview of `draft` (see `mobileSheetFooter`'s doc comment for why). */
|
|
173
|
+
resultCount: number;
|
|
174
|
+
/** `pagination.loading` -- true while a commit-triggered (or any other) refetch is in flight. */
|
|
175
|
+
loading: boolean;
|
|
176
|
+
}
|
|
177
|
+
interface IStyledListingLayoutProps<TFilters = unknown> {
|
|
162
178
|
/**
|
|
163
179
|
* Optional header search box, LIBRARY-wired: name the `TFilters` field it
|
|
164
180
|
* drives via
|
|
@@ -192,6 +208,21 @@ interface IStyledListingLayoutProps {
|
|
|
192
208
|
mapZoom?: number;
|
|
193
209
|
/** Forwarded verbatim to `<ListingMap mapControls={mapControls} />` -- see that prop's doc comment. */
|
|
194
210
|
mapControls?: ReactNode;
|
|
211
|
+
/**
|
|
212
|
+
* Render-prop override for the mobile filters sheet's footer -- when
|
|
213
|
+
* given, replaces the default "Clear all" + "Show N results" buttons
|
|
214
|
+
* entirely, called with the sheet's current draft plus its
|
|
215
|
+
* commit/clear/count/loading state (see `MobileSheetFooterContext`'s own
|
|
216
|
+
* field docs). Exists because the default footer's result count is always
|
|
217
|
+
* the currently APPLIED count (see the class doc's `BottomSheet` section)
|
|
218
|
+
* -- it never previews what applying `draft` WOULD return, since that
|
|
219
|
+
* requires a query only the consumer's own data source can run (e.g. a
|
|
220
|
+
* live-count endpoint keyed off the draft). A consumer with such a source
|
|
221
|
+
* renders its own footer here, driving `apply`/`clear` exactly like the
|
|
222
|
+
* default buttons do. Omitted (the default), the built-in footer renders
|
|
223
|
+
* unchanged.
|
|
224
|
+
*/
|
|
225
|
+
mobileSheetFooter?: (ctx: MobileSheetFooterContext<TFilters>) => ReactNode;
|
|
195
226
|
className?: string;
|
|
196
227
|
}
|
|
197
228
|
/**
|
|
@@ -228,17 +259,36 @@ interface IStyledListingLayoutProps {
|
|
|
228
259
|
* the same `mobileView` state as the CSS toggle. Omitted when there is no
|
|
229
260
|
* map (nothing to toggle to).
|
|
230
261
|
* - `<BottomSheet title="Filters">`: the SAME `<ListingFilters>` component,
|
|
231
|
-
* stacked vertically (`className="rle-filter-stack"`)
|
|
232
|
-
*
|
|
262
|
+
* stacked vertically (`className="rle-filter-stack"`), but in DEFERRED mode
|
|
263
|
+
* (`draft`/`onDraftChange` -- see that component's doc): every control edit
|
|
264
|
+
* inside the sheet buffers into local `draft` state instead of applying to
|
|
265
|
+
* the engine, so the list/map behind the sheet never move while it's open.
|
|
266
|
+
* `draft` is re-synced from the currently applied filters each time the
|
|
267
|
+
* sheet transitions closed -> open (a render-phase adjustment, not an
|
|
268
|
+
* effect). The footer has "Clear all" (resets the DRAFT via
|
|
233
269
|
* `engine.filters.clearedParams()` -- see that method's doc for why a reset
|
|
234
|
-
* round-trips each def's to/fromParams
|
|
235
|
-
*
|
|
236
|
-
*
|
|
270
|
+
* round-trips each def's to/fromParams -- NOT applied until committed) and
|
|
271
|
+
* "Show N results", which commits: `engine.applyFilters(draft)`, then
|
|
272
|
+
* closes the sheet once the resulting refetch settles (or immediately, with
|
|
273
|
+
* no refetch at all, if the draft is unchanged from what's already
|
|
274
|
+
* applied -- see `handleApplyDraft`). While a commit's refetch (or any
|
|
275
|
+
* OTHER live refetch, e.g. the desktop bar or search box, which still apply
|
|
276
|
+
* immediately) is in flight -- `pagination.loading` (`useListingState()`) is
|
|
277
|
+
* true -- the apply button is `disabled` and its label swaps for a
|
|
278
|
+
* `.rle-spinner`, so the sheet reads as "updating" instead of letting the
|
|
279
|
+
* user close onto a stale count. `.rle-sheet__apply` pins a `min-width` so
|
|
280
|
+
* that swap never changes the button's footprint. The result count itself
|
|
281
|
+
* (`Show N results`) always reflects the currently APPLIED results, not a
|
|
282
|
+
* live preview of the draft -- it only changes once a commit lands. A
|
|
283
|
+
* consumer needing a live preview (e.g. its own count endpoint keyed off
|
|
284
|
+
* the draft) can replace this whole footer via the `mobileSheetFooter`
|
|
285
|
+
* render prop -- see `IStyledListingLayoutProps.mobileSheetFooter`'s doc
|
|
286
|
+
* comment; omitted (the default), the footer above renders unchanged.
|
|
237
287
|
* - Fetches the first page itself on mount (`engine.applyFilters({})`) by
|
|
238
288
|
* default -- pass `autoFetch={false}`
|
|
239
289
|
* to opt out and drive the first fetch yourself.
|
|
240
290
|
*/
|
|
241
|
-
declare function StyledListingLayout({ search, toolbarEnd, mobileAction, autoFetch, hasMap: hasMapProp, mapCenter, mapZoom, mapControls, className, }: IStyledListingLayoutProps): react.JSX.Element;
|
|
291
|
+
declare function StyledListingLayout<TFilters = unknown>({ search, toolbarEnd, mobileAction, autoFetch, hasMap: hasMapProp, mapCenter, mapZoom, mapControls, mobileSheetFooter, className, }: IStyledListingLayoutProps<TFilters>): react.JSX.Element;
|
|
242
292
|
|
|
243
293
|
/**
|
|
244
294
|
* Two-shape `map` prop: pass a ready `MapProvider`, or the `{ apiKey, mapId? }`
|
|
@@ -320,6 +370,8 @@ interface ListingAppProps<TFilters> {
|
|
|
320
370
|
* drops the map region entirely in that case).
|
|
321
371
|
*/
|
|
322
372
|
mapControls?: ReactNode;
|
|
373
|
+
/** Forwarded verbatim to `StyledListingLayout`'s `mobileSheetFooter` -- see that prop's doc comment. */
|
|
374
|
+
mobileSheetFooter?: (ctx: MobileSheetFooterContext<TFilters>) => ReactNode;
|
|
323
375
|
config?: Partial<IListingConfigOptions>;
|
|
324
376
|
autoFetch?: boolean;
|
|
325
377
|
className?: string;
|
|
@@ -359,4 +411,4 @@ interface ListingAppProps<TFilters> {
|
|
|
359
411
|
*/
|
|
360
412
|
declare function ListingApp<TEntity, TFilters>(props: ListingAppProps<TFilters>): react.JSX.Element | null;
|
|
361
413
|
|
|
362
|
-
export { BottomNav as B, type ClusterOptions as C, type DatasetDefinition as D, FilterRegistry as F, type IListingConfigOptions as I, ListingApp as L, type MarkerRenderer as M, PaginationMode as P, StyledListingLayout as S, type IListingToolbarProps as a, FallbackPopup as b, type FilterControlProps as c, type FilterDefinition as d, type IListingCardProps as e, type IListingComponents as f, type IListingEmptyProps as g, type IListingFilterPanelProps as h, type IListingLoadingProps as i, type IListingMarkerProps as j, type IListingPopupProps as k, type IListingResultHeaderProps as l, type IListingSearchProps as m, type IListingSidebarProps as n, type ListingAppProps as o, ListingComponentsProvider as p, type
|
|
414
|
+
export { BottomNav as B, type ClusterOptions as C, type DatasetDefinition as D, FilterRegistry as F, type IListingConfigOptions as I, ListingApp as L, type MarkerRenderer as M, PaginationMode as P, StyledListingLayout as S, type IListingToolbarProps as a, FallbackPopup as b, type FilterControlProps as c, type FilterDefinition as d, type IListingCardProps as e, type IListingComponents as f, type IListingEmptyProps as g, type IListingFilterPanelProps as h, type IListingLoadingProps as i, type IListingMarkerProps as j, type IListingPopupProps as k, type IListingResultHeaderProps as l, type IListingSearchProps as m, type IListingSidebarProps as n, type ListingAppProps as o, ListingComponentsProvider as p, type MobileSheetFooterContext as q, type BottomNavView as r, type IBottomNavAction as s, type IBottomNavProps as t, useListingComponents as u, type IStyledListingLayoutProps as v, type ListingAppMapProp as w };
|
package/dist/styled/index.cjs
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
1
|
"use strict";Object.defineProperty(exports, "__esModule", {value: true});"use client";
|
|
2
|
-
var
|
|
2
|
+
var _chunkHTNCZ5NScjs = require('../chunk-HTNCZ5NS.cjs');var _jsxruntime = require('react/jsx-runtime');function L({children:o}){return _jsxruntime.jsx.call(void 0, _chunkHTNCZ5NScjs.q,{..._chunkHTNCZ5NScjs.O,children:o})}exports.BottomNav = _chunkHTNCZ5NScjs.P; exports.BottomSheet = _chunkHTNCZ5NScjs.Q; exports.ListingApp = _chunkHTNCZ5NScjs.S; exports.StyledCard = _chunkHTNCZ5NScjs.E; exports.StyledComponentsProviderWithDefaults = L; exports.StyledEmpty = _chunkHTNCZ5NScjs.F; exports.StyledFilterPanel = _chunkHTNCZ5NScjs.G; exports.StyledListingLayout = _chunkHTNCZ5NScjs.R; exports.StyledLoading = _chunkHTNCZ5NScjs.H; exports.StyledMarker = _chunkHTNCZ5NScjs.I; exports.StyledPopup = _chunkHTNCZ5NScjs.J; exports.StyledResultHeader = _chunkHTNCZ5NScjs.K; exports.StyledSearch = _chunkHTNCZ5NScjs.L; exports.StyledSidebar = _chunkHTNCZ5NScjs.M; exports.StyledToolbar = _chunkHTNCZ5NScjs.N; exports.styledDefaultComponents = _chunkHTNCZ5NScjs.O;
|
package/dist/styled/index.d.cts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import * as react from 'react';
|
|
2
2
|
import { ReactNode } from 'react';
|
|
3
|
-
import { e as IListingCardProps, g as IListingEmptyProps, h as IListingFilterPanelProps, i as IListingLoadingProps, j as IListingMarkerProps, k as IListingPopupProps, l as IListingResultHeaderProps, m as IListingSearchProps, n as IListingSidebarProps, a as IListingToolbarProps, f as IListingComponents } from '../listing-app-
|
|
4
|
-
export { B as BottomNav,
|
|
3
|
+
import { e as IListingCardProps, g as IListingEmptyProps, h as IListingFilterPanelProps, i as IListingLoadingProps, j as IListingMarkerProps, k as IListingPopupProps, l as IListingResultHeaderProps, m as IListingSearchProps, n as IListingSidebarProps, a as IListingToolbarProps, f as IListingComponents } from '../listing-app-BKE75k--.cjs';
|
|
4
|
+
export { B as BottomNav, r as BottomNavView, s as IBottomNavAction, t as IBottomNavProps, v as IStyledListingLayoutProps, L as ListingApp, w as ListingAppMapProp, o as ListingAppProps, q as MobileSheetFooterContext, S as StyledListingLayout } from '../listing-app-BKE75k--.cjs';
|
|
5
5
|
import '../map-provider.interface-B5Law7gE.cjs';
|
|
6
6
|
|
|
7
7
|
/**
|
package/dist/styled/index.d.ts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import * as react from 'react';
|
|
2
2
|
import { ReactNode } from 'react';
|
|
3
|
-
import { e as IListingCardProps, g as IListingEmptyProps, h as IListingFilterPanelProps, i as IListingLoadingProps, j as IListingMarkerProps, k as IListingPopupProps, l as IListingResultHeaderProps, m as IListingSearchProps, n as IListingSidebarProps, a as IListingToolbarProps, f as IListingComponents } from '../listing-app-
|
|
4
|
-
export { B as BottomNav,
|
|
3
|
+
import { e as IListingCardProps, g as IListingEmptyProps, h as IListingFilterPanelProps, i as IListingLoadingProps, j as IListingMarkerProps, k as IListingPopupProps, l as IListingResultHeaderProps, m as IListingSearchProps, n as IListingSidebarProps, a as IListingToolbarProps, f as IListingComponents } from '../listing-app-CRGXBErM.js';
|
|
4
|
+
export { B as BottomNav, r as BottomNavView, s as IBottomNavAction, t as IBottomNavProps, v as IStyledListingLayoutProps, L as ListingApp, w as ListingAppMapProp, o as ListingAppProps, q as MobileSheetFooterContext, S as StyledListingLayout } from '../listing-app-CRGXBErM.js';
|
|
5
5
|
import '../map-provider.interface-B5Law7gE.js';
|
|
6
6
|
|
|
7
7
|
/**
|
package/dist/styled/index.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
1
|
"use client";
|
|
2
|
-
import{E as r,F as p,G as i,H as
|
|
2
|
+
import{E as r,F as p,G as i,H as y,I as d,J as l,K as n,L as m,M as s,N as a,O as t,P as S,Q as f,R as P,S as u,q as e}from"../chunk-CJQJDGBU.js";import{jsx as g}from"react/jsx-runtime";function L({children:o}){return g(e,{...t,children:o})}export{S as BottomNav,f as BottomSheet,u as ListingApp,r as StyledCard,L as StyledComponentsProviderWithDefaults,p as StyledEmpty,i as StyledFilterPanel,P as StyledListingLayout,y as StyledLoading,d as StyledMarker,l as StyledPopup,n as StyledResultHeader,m as StyledSearch,s as StyledSidebar,a as StyledToolbar,t as styledDefaultComponents};
|
package/dist/styles.css
CHANGED
|
@@ -362,6 +362,31 @@
|
|
|
362
362
|
}
|
|
363
363
|
}
|
|
364
364
|
|
|
365
|
+
/* Small inline spinner for in-flight async state on a button (e.g. the mobile
|
|
366
|
+
filters sheet's apply button while a filter-triggered refetch is loading).
|
|
367
|
+
`currentColor` borders so it inherits whatever text color the host button
|
|
368
|
+
already sets (e.g. `--rle-primary-contrast` on `.rle-btn--primary`); the
|
|
369
|
+
transparent top edge is what reads as a moving notch once it spins. Covered
|
|
370
|
+
by the blanket `prefers-reduced-motion` rule at the end of this file (every
|
|
371
|
+
`rle-`-prefixed class has its `animation` dropped there), so it degrades to
|
|
372
|
+
a static ring rather than a separate opt-out here. */
|
|
373
|
+
.rle-spinner {
|
|
374
|
+
display: inline-block;
|
|
375
|
+
width: 16px;
|
|
376
|
+
height: 16px;
|
|
377
|
+
border: 2px solid currentColor;
|
|
378
|
+
border-top-color: transparent;
|
|
379
|
+
border-radius: 50%;
|
|
380
|
+
opacity: 0.85;
|
|
381
|
+
animation: rle-spin 0.75s linear infinite;
|
|
382
|
+
}
|
|
383
|
+
|
|
384
|
+
@keyframes rle-spin {
|
|
385
|
+
to {
|
|
386
|
+
transform: rotate(360deg);
|
|
387
|
+
}
|
|
388
|
+
}
|
|
389
|
+
|
|
365
390
|
.rle-result-header {
|
|
366
391
|
font-size: var(--rle-fs-md);
|
|
367
392
|
color: var(--rle-muted);
|
|
@@ -1015,6 +1040,12 @@
|
|
|
1015
1040
|
border-top: 1px solid var(--rle-border);
|
|
1016
1041
|
}
|
|
1017
1042
|
|
|
1043
|
+
/* Pinned so swapping "Show N results" for `.rle-spinner` while
|
|
1044
|
+
`pagination.loading` is true never collapses/reflows the button. */
|
|
1045
|
+
.rle-sheet__apply {
|
|
1046
|
+
min-width: 9.5rem;
|
|
1047
|
+
}
|
|
1048
|
+
|
|
1018
1049
|
/* -----------------------------------------------------------------------
|
|
1019
1050
|
* Motion -- LAST on purpose: prefix-scoped like the base reset (every
|
|
1020
1051
|
* `rle-` element goes still, so a new component with a transition can't be
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "react-listing-engine",
|
|
3
|
-
"version": "0.7.
|
|
3
|
+
"version": "0.7.5",
|
|
4
4
|
"license": "MIT",
|
|
5
5
|
"description": "Headless, composable listing engine for React: filterable list + Google-Maps multi-layer map, with pluggable data adapters, a filter/dataset registry, injectable components, and a Tailwind-free styled adapter.",
|
|
6
6
|
"funding": [
|
package/dist/chunk-TX6KIOD7.js
DELETED
|
@@ -1,2 +0,0 @@
|
|
|
1
|
-
"use client";
|
|
2
|
-
var Q=class{state;listeners=new Set;constructor(e){this.state=this.freezeState({filters:{...e.filters},results:{items:[],nextCursor:null},bounds:null,selection:null,hovered:null,pagination:{mode:e.mode??"paged",loading:!1},layers:{},points:{}})}getState(){return this.state}setFilters(e){this.setState({filters:{...this.state.filters,...e}})}setResults(e){this.setState({results:{items:[...e.items],nextCursor:e.nextCursor,total:e.total}})}appendResults(e){this.setState({results:{items:[...this.state.results.items,...e.items],nextCursor:e.nextCursor,total:e.total}})}setBounds(e){this.setState({bounds:e?{...e}:null})}setSelection(e){this.setState({selection:e})}setHovered(e){this.setState({hovered:e})}setLayerVisible(e,i){this.setState({layers:{...this.state.layers,[e]:i}})}setLoading(e){this.setState({pagination:{...this.state.pagination,loading:e}})}setPoints(e,i){this.setState({points:{...this.state.points,[e]:[...i]}})}subscribe(e){return this.listeners.add(e),()=>{this.listeners.delete(e)}}setState(e){this.state=this.freezeState({...this.state,...e}),this.notify()}notify(){for(let e of this.listeners)e()}freezeState(e){Object.freeze(e.filters),Object.freeze(e.results.items),Object.freeze(e.results),e.bounds&&Object.freeze(e.bounds),Object.freeze(e.pagination),Object.freeze(e.layers);for(let i of Object.values(e.points))Object.freeze(i);return Object.freeze(e.points),Object.freeze(e)}};var H=class{defs=new Map;add(e){if(this.defs.has(e.key))throw new Error(`FilterRegistry: filter "${e.key}" is already registered`);return this.defs.set(e.key,{...e}),this}remove(e){return this.defs.delete(e),this}replace(e,i){if(!this.defs.has(e))throw new Error(`FilterRegistry: cannot replace unregistered filter "${e}"`);return this.defs.set(e,{...i,key:e}),this}reorder(e){let i=this.list(),r=e.filter(o=>this.defs.has(o));r.forEach((o,n)=>{this.defs.get(o).order=n});let s=new Set(r);return i.filter(o=>!s.has(o.key)).forEach((o,n)=>{o.order=r.length+n}),this}list(){return[...this.defs.values()].sort((e,i)=>e.order-i.order)}has(e){return this.defs.has(e)}toFilters(e){return this.list().filter(r=>Object.hasOwn(e,r.key)).map(r=>r.toParams(e[r.key])).reduce((r,s)=>({...r,...s}),{})}activeKeys(e){return this.list().filter(i=>i.isActive?.(e)).map(i=>i.key)}clearedParams(){return this.list().reduce((e,i)=>Object.assign(e,i.toParams(i.fromParams({}))),{})}};var G=class{defs=new Map;add(e){if(this.defs.has(e.id))throw new Error(`DatasetRegistry: dataset "${e.id}" is already registered`);return this.defs.set(e.id,{...e}),this}get(e){return this.defs.get(e)}has(e){return this.defs.has(e)}list(){return[...this.defs.values()]}visibleIds(){return this.list().filter(e=>e.visible?.()!==!1).map(e=>e.id)}};var Z=class{map=new Map;dispose(){this.map.clear()}emit(e){let i=this.map.get(e.type);if(i)for(let s of[...i])s(e);let r=this.map.get("*");if(r)for(let s of[...r])s(e)}on(e,i){let r=this.map.get(e);return r||(r=new Set,this.map.set(e,r)),r.add(i),()=>{r.delete(i)}}};var Ce={pagination:"paged",pageSize:20,debounceMs:250};var X=class{options;constructor(e){this.options=Object.freeze({...Ce,...e})}};var J=class{filters;map;datasets;primaryDatasetId;store;emitter=new Z;config;debounceTimer=null;debounceResolve=null;queryToken=0;pointsToken=0;constructor(e){this.datasets=e.datasets,this.filters=e.filters??new H,this.map=e.map,this.config=new X(e.config);let i=e.primaryDatasetId??this.datasets.list()[0]?.id;if(i==null||!this.datasets.has(i))throw new Error(`ListingEngine: primary dataset "${i??""}" is not registered \u2014 pass a valid primaryDatasetId or register at least one dataset`);this.primaryDatasetId=i,this.store=new Q({filters:e.initialFilters??{},mode:this.config.options.pagination})}get state(){return this.store.getState()}get options(){return this.config.options}applyFilters(e){this.store.setFilters(e),this.emitter.emit({type:"FiltersChanged",filters:this.currentFilters()}),this.clearDebounce();let i=++this.queryToken,r=this.config.options.debounceMs;return r<=0?this.runQuery(i):new Promise(s=>{this.debounceResolve=s,this.debounceTimer=setTimeout(()=>{this.debounceTimer=null,this.debounceResolve=null,s(this.runQuery(i))},r)})}async loadPage(){let e=this.state.results.nextCursor;if(e===null)return;let i=++this.queryToken,r=this.primaryDataset();this.store.setLoading(!0);try{let s=await r.adapter.list(this.currentFilters(),{cursor:e,limit:this.config.options.pageSize});if(i!==this.queryToken)return;this.config.options.pagination==="infinite"?this.store.appendResults(s):this.store.setResults(s),this.emitter.emit({type:"ResultsLoaded",datasetId:this.primaryDatasetId,count:s.items.length})}finally{i===this.queryToken&&this.store.setLoading(!1)}}async loadPoints(e){this.store.setBounds(e),this.emitter.emit({type:"BoundsChanged",bounds:e});let i=this.currentFilters(),r=++this.pointsToken;await Promise.allSettled(this.datasets.visibleIds().map(async s=>{let o=this.datasets.get(s);if(!o)return;let n=await o.adapter.getPoints(i,e);r===this.pointsToken&&this.store.setPoints(s,n)}))}selectPoint(e,i){this.store.setSelection(i);let r=this.state.points[e]?.find(s=>s.id===i);r&&this.emitter.emit({type:"PointClicked",datasetId:e,id:r.id,entity:r.entity})}setHovered(e,i){this.store.setHovered(i)}toggleLayer(e){let r=!(this.state.layers[e]??!0);this.store.setLayerVisible(e,r),this.emitter.emit({type:"LayerToggled",datasetId:e,visible:r})}subscribe(e){return this.store.subscribe(e)}on(e,i){return this.emitter.on(e,i)}dispose(){this.clearDebounce(),this.emitter.dispose()}async runQuery(e){if(e!==this.queryToken)return;let i=this.primaryDataset();this.store.setLoading(!0);try{let r=await i.adapter.list(this.currentFilters(),{cursor:null,limit:this.config.options.pageSize});if(e!==this.queryToken)return;this.store.setResults(r),this.emitter.emit({type:"ResultsLoaded",datasetId:this.primaryDatasetId,count:r.items.length})}finally{e===this.queryToken&&this.store.setLoading(!1)}}primaryDataset(){return this.datasets.get(this.primaryDatasetId)}currentFilters(){return this.store.getState().filters}clearDebounce(){this.debounceTimer!==null&&(clearTimeout(this.debounceTimer),this.debounceTimer=null),this.debounceResolve!==null&&(this.debounceResolve(),this.debounceResolve=null)}};function Se(...t){let e={config:{},filters:new H,datasets:new G};for(let i of t)i(e);return e}var Ie=t=>e=>{e.config={...e.config,...t}},we=t=>e=>{e.map=t},ke=t=>e=>{e.datasets.add(t)},Ee=t=>e=>{t(e.filters)},yi=t=>e=>{e.urlSync=t},xe=t=>e=>{e.initialFilters=t},vi=t=>e=>{e.primaryDatasetId=t};import{createContext as it,useContext as rt}from"react";import{jsx as S,jsxs as gt}from"react/jsx-runtime";function nt(t){return String(t?.title??"")}var st=({item:t})=>S("div",{children:nt(t)}),ot=()=>S("div",{}),le=()=>S("div",{}),at=({children:t})=>S("div",{children:t}),lt=({children:t})=>S("div",{children:t}),dt=({value:t,onChange:e,placeholder:i})=>S("input",{type:"search",value:t,placeholder:i,onChange:r=>e(r.target.value),"aria-label":i??"Search"}),pt=()=>S("div",{role:"status",children:"No results"}),ct=()=>S("div",{role:"status","aria-busy":"true",children:"Loading\u2026"}),ut=({count:t})=>gt("div",{children:[t," results"]}),mt=({children:t})=>S("div",{children:t}),C={Card:st,Marker:ot,Popup:le,Sidebar:at,FilterPanel:lt,Search:dt,Empty:pt,Loading:ct,ResultHeader:ut,Toolbar:mt},Ne=it(C);function Re(t){let{Card:e,Marker:i,Popup:r,Sidebar:s,FilterPanel:o,Search:n,Empty:a,Loading:d,ResultHeader:l,Toolbar:c,children:h}=t,b={Card:e??C.Card,Marker:i??C.Marker,Popup:r??C.Popup,Sidebar:s??C.Sidebar,FilterPanel:o??C.FilterPanel,Search:n??C.Search,Empty:a??C.Empty,Loading:d??C.Loading,ResultHeader:l??C.ResultHeader,Toolbar:c??C.Toolbar};return S(Ne.Provider,{value:b,children:h})}function P(){return rt(Ne)}import{createContext as ft}from"react";var Y=ft(null);import{useContext as yt}from"react";function g(){let t=yt(Y);if(t===null)throw new Error("useListing must be used within a <ListingProvider>");return t}import{useCallback as Me,useSyncExternalStore as vt}from"react";function I(){let t=g(),e=Me(r=>t.subscribe(r),[t]),i=Me(()=>t.state,[t]);return vt(e,i,i)}import{useCallback as De}from"react";function ee(){let t=g(),e=I(),i=De(s=>t.applyFilters(s),[t]),r=De((s,o)=>t.applyFilters({[s]:o}),[t]);return{filters:e.filters,set:i,setField:r}}import{jsx as $,jsxs as ht}from"react/jsx-runtime";function de({className:t,groupClassName:e,hideLabels:i}={}){let r=g(),{FilterPanel:s}=P(),{filters:o}=ee();return $(s,{children:$("div",{className:t??"space-y-5",children:r.filters.list().map(n=>{if(typeof n.render=="string")return $("div",{"data-filter":n.key,className:e},n.key);let a=n.render;return ht("div",{className:e,children:[n.label&&!i&&$("div",{className:"mb-1.5 text-[13px] font-medium text-foreground",children:n.label}),$(a,{value:n.fromParams(o),onChange:d=>{r.applyFilters(n.toParams(d))}})]},n.key)})})})}function z(){return I().results}import{jsx as te}from"react/jsx-runtime";function Lt(t,e){if(t&&typeof t=="object"&&"id"in t){let i=t.id;if(typeof i=="string"||typeof i=="number")return i}return e}function Oe({className:t}={}){let e=g(),{items:i}=z(),{pagination:r,selection:s}=I(),{Card:o,Empty:n,Loading:a}=P();return r.loading&&i.length===0?te(a,{}):i.length===0?te(n,{}):te("div",{role:"list",className:t,children:i.map((d,l)=>{let c=Lt(d,l);return te(o,{item:d,selected:s===c,onSelect:()=>e.selectPoint(e.primaryDatasetId,c)},c)})})}import{useEffect as W,useRef as B,useState as _e}from"react";import{createPortal as bt}from"react-dom";import{jsx as pe,jsxs as He}from"react/jsx-runtime";var Pt={west:-179.9,south:-85,east:179.9,north:85},Be=.1,Ae=.02;function Tt(t){if(t.length===0)return null;let e=t[0].lng,i=t[0].lng,r=t[0].lat,s=t[0].lat;for(let{lat:a,lng:d}of t)d<e&&(e=d),d>i&&(i=d),a<r&&(r=a),a>s&&(s=a);let o=s>r?(s-r)*Be:Ae,n=i>e?(i-e)*Be:Ae;return{west:e-n,east:i+n,south:r-o,north:s+o}}function ze(t){let{center:e,zoom:i,fallback:r,mapControls:s}=t,o=g(),n=I(),a=B(null),d=B(null),l=B(null),[c,h]=_e(!1),b=B(!1),w=B(!1),k=B(!1),p=o.map;W(()=>{let L=l.current;if(!p||!L)return;let f=[];for(let u of Object.keys(n.points)){if(n.layers[u]===!1)continue;let y=o.datasets.get(u),R=n.points[u]??[],ae={id:u,markers:R.map(M=>({id:M.id,position:M.position,iconUrl:y?.marker.iconUrl?.(M.entity),element:y?.marker.element?.(M.entity)})),clustering:y?.clustering,onMarkerClick:M=>o.selectPoint(u,M)};f.push(p.renderLayer(L,ae))}return()=>{f.forEach(u=>u())}},[o,p,c,n.points,n.layers]),W(()=>{if(!a.current||!p)return;let L=a.current,f=!1,u=null;return(async()=>{let y=await p.mount(L,{center:e,zoom:i,fullscreenTarget:d.current??void 0});if(f){p.destroy(y);return}l.current=y,u=p.onBoundsChange(y,R=>{k.current?k.current=!1:w.current=!0,o.loadPoints(R)}),h(!0),o.loadPoints(Pt)})(),()=>{f=!0,u?.(),l.current&&(p.destroy(l.current),l.current=null),h(!1)}},[o,p]),W(()=>{let L=l.current;if(!p||!L||e||b.current||w.current)return;let f=[];for(let y of Object.keys(n.points))if(n.layers[y]!==!1)for(let R of n.points[y]??[])f.push(R.position);let u=Tt(f);u&&(b.current=!0,k.current=!0,p.fitBounds(L,u))},[p,e,c,n.points,n.layers]),W(()=>{p?.updateMarkerStates(n.selection,n.hovered)},[p,c,n.selection,n.hovered]);let{Popup:F}=P(),O=F!==le,_=n.points[o.primaryDatasetId]??[],A=n.selection!=null?_.find(L=>L.id===n.selection):void 0,[V,j]=_e(null),N=B(A);return N.current=A,W(()=>{let L=l.current;if(!p||!L||!O)return;let f=N.current;if(!f)return;let u=p.mountOverlay(f.position);j({entity:f.entity,position:f.position,container:u.container});let y=()=>o.selectPoint(o.primaryDatasetId,null),R=M=>{M.key==="Escape"&&y()};document.addEventListener("keydown",R);let ae=p.onMapClick(y);return()=>{document.removeEventListener("keydown",R),ae(),u.unmount(),j(null)}},[o,p,c,n.selection,O]),He("div",{ref:d,className:"relative h-full min-h-0 w-full",children:[He("div",{ref:a,className:!p&&r?"flex h-full min-h-0 w-full items-center justify-center":"h-full min-h-0 w-full",children:[!p&&r,O&&V?bt(pe(F,{entity:V.entity,onClose:()=>o.selectPoint(o.primaryDatasetId,null)}),V.container):null]}),s!=null&&pe("div",{className:"pointer-events-none absolute inset-0",children:pe("div",{className:"pointer-events-auto",children:s})})]})}import{jsx as Ft}from"react/jsx-runtime";function Ke(){let t=g(),{results:e,pagination:i}=I();return e.nextCursor==null?null:Ft("button",{type:"button",disabled:i.loading,onClick:()=>{t.loadPage()},children:"Load more"})}import{jsx as Ct}from"react/jsx-runtime";function Ue(){let{items:t,total:e}=z(),{ResultHeader:i}=P();return Ct(i,{count:t.length,total:e})}import{useEffect as St,useRef as It}from"react";function Ve(t,e){let i=g(),r=It(e);r.current=e,St(()=>i.on(t,s=>r.current(s)),[i,t])}import{useEffect as wt,useState as $e}from"react";import{jsx as kt}from"react/jsx-runtime";function We(t){let{children:e,...i}=t,[r]=$e(()=>i),[s,o]=$e(null);return wt(()=>{let n=new J({datasets:r.datasets,filters:r.filters,config:r.config,map:r.map,initialFilters:r.initialFilters,primaryDatasetId:r.primaryDatasetId});return r.urlSync&&r.urlSync.start(n),o(n),()=>{r.urlSync&&r.urlSync.stop(),n.dispose(),o(a=>a===n?null:a)}},[r]),s?kt(Y.Provider,{value:s,children:e}):null}function K(t){return typeof t!="number"?t:new Intl.NumberFormat("en-US",{style:"currency",currency:"USD",maximumFractionDigits:0}).format(t)}import{Fragment as xt,jsx as E,jsxs as qe}from"react/jsx-runtime";function Et(t){return t?"rle-card rle-card--selected":"rle-card"}function ce({item:t,selected:e,onSelect:i}){let r=t??{},s=Et(e),o=qe(xt,{children:[r.imageUrl?E("img",{src:r.imageUrl,alt:r.title??"",className:"rle-card-media"}):E("div",{className:"rle-card-media rle-card-media--placeholder","aria-hidden":"true"}),qe("div",{className:"rle-card-body",children:[r.title&&E("span",{className:"rle-card-title",children:r.title}),r.subtitle&&E("span",{className:"rle-card-address",children:r.subtitle}),r.badge&&E("div",{className:"rle-card-info",children:E("span",{className:"rle-card-info-item",children:r.badge})}),r.price!=null&&E("span",{className:"rle-card-price",children:K(r.price)})]})]});return i?E("button",{type:"button",onClick:i,"aria-pressed":e??!1,className:s,children:o}):E("article",{className:s,children:o})}import{jsx as ie,jsxs as je}from"react/jsx-runtime";function ue(t){return je("div",{role:"status",className:"rle-empty",children:[je("svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:1.5,strokeLinecap:"round",strokeLinejoin:"round",className:"rle-empty-icon","aria-hidden":"true",children:[ie("circle",{cx:"11",cy:"11",r:"7"}),ie("path",{d:"m21 21-4.3-4.3"})]}),ie("p",{className:"rle-empty-title",children:"No results"}),ie("p",{className:"rle-empty-hint",children:"Try adjusting your filters or search terms."})]})}import{jsx as Nt}from"react/jsx-runtime";function me({children:t}){return Nt("div",{className:"rle-filter-panel",children:t})}import{jsx as re,jsxs as Rt}from"react/jsx-runtime";function ge(t){return re("div",{className:"rle-loading",role:"status","aria-busy":"true","aria-label":"Loading results",children:Array.from({length:3}).map((e,i)=>Rt("div",{className:"rle-loading-item",children:[re("div",{className:"rle-skeleton",style:{aspectRatio:"4 / 3",width:"100%"}}),re("div",{className:"rle-skeleton",style:{height:16,width:"65%"}}),re("div",{className:"rle-skeleton",style:{height:12,width:"35%"}})]},i))})}import{jsx as Mt}from"react/jsx-runtime";function fe({point:t}){let e=t.entity??{};return Mt("span",{className:"rle-pin",children:e.price!=null?K(e.price):""})}import{jsx as U,jsxs as ye}from"react/jsx-runtime";function ve({entity:t,onClose:e}){let i=t??{};return ye("div",{className:"rle-popup",role:"group","aria-label":"Location details",children:[U("button",{type:"button",onClick:e,"aria-label":"Close",className:"rle-popup-close",children:ye("svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round",width:"16",height:"16","aria-hidden":"true",children:[U("path",{d:"M18 6 6 18"}),U("path",{d:"m6 6 12 12"})]})}),ye("div",{children:[i.title&&U("div",{className:"rle-card-title",children:i.title}),i.subtitle&&U("div",{className:"rle-card-address",children:i.subtitle}),i.price!=null&&U("div",{className:"rle-card-price",children:K(i.price)})]})]})}import{jsx as Dt}from"react/jsx-runtime";function he({count:t,total:e}){let i=e!=null&&e!==t?`${t} of ${e} results`:`${t} results`;return Dt("div",{className:"rle-result-header",children:i})}import{jsx as Ot}from"react/jsx-runtime";function Le({value:t,onChange:e,placeholder:i}){return Ot("input",{type:"search",value:t,placeholder:i,onChange:r=>e(r.target.value),"aria-label":i??"Search",className:"rle-input"})}import{jsx as _t}from"react/jsx-runtime";function be({children:t}){return _t("aside",{className:"rle-sidebar",children:t})}import{jsx as Bt}from"react/jsx-runtime";function Pe({children:t}){return Bt("div",{className:"rle-toolbar",children:t})}var Qe={Card:ce,Marker:fe,Popup:ve,Sidebar:be,FilterPanel:me,Search:Le,Empty:ue,Loading:ge,ResultHeader:he,Toolbar:Pe};import{jsx as T,jsxs as q}from"react/jsx-runtime";function Ge({view:t,onViewChange:e}){return T("nav",{className:"rle-bottom-nav","aria-label":"Listing navigation",children:q("div",{className:"rle-viewtoggle",role:"group","aria-label":"View",children:[q("button",{type:"button",className:`rle-viewtoggle__btn${t==="list"?" rle-viewtoggle__btn--active":""}`,"aria-pressed":t==="list",onClick:()=>e("list"),children:[T(At,{}),"List"]}),q("button",{type:"button",className:`rle-viewtoggle__btn${t==="map"?" rle-viewtoggle__btn--active":""}`,"aria-pressed":t==="map",onClick:()=>e("map"),children:[T(Ht,{}),"Map"]})]})})}function At(){return q("svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round",width:"16",height:"16","aria-hidden":"true",children:[T("line",{x1:"8",y1:"6",x2:"20",y2:"6"}),T("line",{x1:"8",y1:"12",x2:"20",y2:"12"}),T("line",{x1:"8",y1:"18",x2:"20",y2:"18"}),T("line",{x1:"4",y1:"6",x2:"4.01",y2:"6"}),T("line",{x1:"4",y1:"12",x2:"4.01",y2:"12"}),T("line",{x1:"4",y1:"18",x2:"4.01",y2:"18"})]})}function Ht(){return q("svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round",width:"16",height:"16","aria-hidden":"true",children:[T("polygon",{points:"1 6 8 3 16 6 23 3 23 18 16 21 8 18 1 21 1 6"}),T("line",{x1:"8",y1:"3",x2:"8",y2:"18"}),T("line",{x1:"16",y1:"6",x2:"16",y2:"21"})]})}import{useEffect as Te,useRef as zt,useState as Ze}from"react";import{createPortal as Kt}from"react-dom";import{Fragment as Vt,jsx as x,jsxs as ne}from"react/jsx-runtime";function Xe({open:t,onOpenChange:e,title:i,children:r,footer:s}){let o=zt(null),[n,a]=Ze(!1),[d,l]=Ze(!1);return Te(()=>{if(!t){l(!1),a(!1);return}a(!0);let c=requestAnimationFrame(()=>l(!0));return()=>cancelAnimationFrame(c)},[t]),Te(()=>{if(!n)return;let c=document.body.style.overflow;return document.body.style.overflow="hidden",()=>{document.body.style.overflow=c}},[n]),Te(()=>{if(!n)return;o.current?.focus();function c(h){h.key==="Escape"&&e(!1)}return document.addEventListener("keydown",c),()=>document.removeEventListener("keydown",c)},[n,e]),!n||typeof document>"u"?null:Kt(ne(Vt,{children:[x("div",{className:`rle-sheet-backdrop${d?" rle-sheet-backdrop--open":""}`,onClick:()=>e(!1),"aria-hidden":"true"}),ne("div",{ref:o,className:`rle-sheet${d?" rle-sheet--open":""}`,role:"dialog","aria-modal":"true","aria-label":i,tabIndex:-1,children:[x("div",{className:"rle-sheet__handle","aria-hidden":"true"}),ne("div",{className:"rle-sheet__header",children:[i&&x("div",{className:"rle-sheet__title",children:i}),x("button",{type:"button",className:"rle-sheet__close",onClick:()=>e(!1),"aria-label":"Close",children:x(Ut,{})})]}),x("div",{className:"rle-sheet__body",children:r}),s&&x("div",{className:"rle-sheet__footer",children:s})]})]}),document.body)}function Ut(){return ne("svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round",width:"16",height:"16","aria-hidden":"true",children:[x("path",{d:"M18 6 6 18"}),x("path",{d:"m6 6 12 12"})]})}import{useEffect as Ye,useRef as qt,useState as oe}from"react";import{jsx as v,jsxs as se}from"react/jsx-runtime";function Je({search:t,onFiltersClick:e,filterCount:i=0,action:r}){let{Search:s}=P();return se("header",{className:"rle-mobile-header",children:[t&&v("div",{className:"rle-mobile-header__search",children:v(s,{value:t.value,onChange:t.onChange,placeholder:t.placeholder})}),se("button",{type:"button",className:"rle-btn rle-mobile-header__btn",onClick:e,children:[v($t,{}),v("span",{children:"Filters"}),i>0&&v("span",{className:"rle-mobile-header__count",children:i})]}),r&&v("button",{type:"button",className:"rle-btn rle-mobile-header__btn rle-mobile-header__btn--icon",onClick:r.onClick,"aria-label":r.label,children:r.icon??v(Wt,{})})]})}function $t(){return se("svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round","aria-hidden":"true",children:[v("line",{x1:"4",y1:"6",x2:"20",y2:"6"}),v("circle",{cx:"9",cy:"6",r:"2",fill:"currentColor",stroke:"none"}),v("line",{x1:"4",y1:"12",x2:"20",y2:"12"}),v("circle",{cx:"15",cy:"12",r:"2",fill:"currentColor",stroke:"none"}),v("line",{x1:"4",y1:"18",x2:"20",y2:"18"}),v("circle",{cx:"11",cy:"18",r:"2",fill:"currentColor",stroke:"none"})]})}function Wt(){return se("svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round","aria-hidden":"true",children:[v("line",{x1:"12",y1:"5",x2:"12",y2:"19"}),v("line",{x1:"5",y1:"12",x2:"19",y2:"12"})]})}import{Fragment as Gt,jsx as m,jsxs as D}from"react/jsx-runtime";var jt=m("div",{className:"rle-empty",children:"Map unavailable"});function Qt(){let t=qt(null),[e,i]=oe(!0),[r,s]=oe(!0);return Ye(()=>{let o=t.current;if(!o)return;let n=()=>{let{clientWidth:h,scrollLeft:b,scrollWidth:w}=o;i(b<=0),s(b+h>=w-1)},a=0,d=()=>{a||(a=requestAnimationFrame(()=>{a=0,n()}))};n(),o.addEventListener("scroll",n,{passive:!0});let l,c;return typeof ResizeObserver<"u"&&(l=new ResizeObserver(n),l.observe(o)),typeof MutationObserver<"u"&&(c=new MutationObserver(d),c.observe(o,{characterData:!0,childList:!0,subtree:!0})),()=>{o.removeEventListener("scroll",n),l?.disconnect(),c?.disconnect(),a&&cancelAnimationFrame(a)}},[]),{atEnd:r,atStart:e,ref:t}}function et({search:t,toolbarEnd:e,mobileAction:i,autoFetch:r=!0,hasMap:s,mapCenter:o,mapZoom:n,mapControls:a,className:d}){let l=g(),{Search:c}=P(),h=z(),{filters:b,set:w}=ee(),k=s??l.map!=null,[p,F]=oe("list"),[O,_]=oe(!1),{atEnd:A,atStart:V,ref:j}=Qt(),N=t?{value:String(b[t.filterKey]??""),onChange:y=>{w({[t.filterKey]:y||void 0})},placeholder:t.placeholder}:void 0;Ye(()=>{r!==!1&&l.applyFilters({})},[l,r]);let L=()=>{w(l.filters.clearedParams())},f=l.filters.activeKeys(b).length,u=h.total??h.items.length;return D("div",{className:d?`rle-app ${d}`:"rle-app",children:[D("div",{className:"rle-filter-bar",children:[D("div",{className:"rle-filter-bar__scroll",ref:j,children:[N&&m("div",{className:"rle-filter-bar__search",children:m(c,{value:N.value,onChange:N.onChange,placeholder:N.placeholder})}),m(de,{className:"rle-filters-row",groupClassName:"rle-filter-group",hideLabels:!0})]}),!V&&m("div",{className:"rle-filter-bar__fade rle-filter-bar__fade--start","aria-hidden":"true"}),!A&&m("div",{className:"rle-filter-bar__fade rle-filter-bar__fade--end","aria-hidden":"true"})]}),m(Je,{search:N,onFiltersClick:()=>_(!0),filterCount:f,action:i}),D("div",{className:`rle-body ${k?"rle-split":"rle-body--list-only"}`,"data-mobile-view":p,children:[D("div",{className:"rle-list",children:[D("div",{className:"rle-list-header",children:[m(Ue,{}),e&&m("div",{className:"rle-list-header__toolbar",children:e})]}),m(Oe,{className:"rle-list-grid"}),m(Ke,{})]}),k&&m("div",{className:"rle-map",children:m(ze,{center:o,zoom:n,fallback:jt,mapControls:a})})]}),k&&m(Ge,{view:p,onViewChange:F}),m(Xe,{title:"Filters",open:O,onOpenChange:_,footer:D(Gt,{children:[m("button",{type:"button",className:"rle-btn rle-btn--ghost",onClick:L,children:"Clear all"}),D("button",{type:"button",className:"rle-btn rle-btn--primary",onClick:()=>_(!1),children:["Show ",u," results"]})]}),children:m(de,{className:"rle-filter-stack",groupClassName:"rle-filter-group"})})]})}import{useEffect as Zt,useRef as Xt,useState as Jt}from"react";import{jsx as Fe,jsxs as ti}from"react/jsx-runtime";function tt(t){return"provider"in t}function Yt(t){let e=t!=null&&!tt(t),i=e?t.apiKey:void 0,r=e?t.mapId:void 0,s=e?t.mapOptions:void 0,o=e?t.styles:void 0,[n,a]=Jt(()=>!t||tt(t)?{ready:!0,provider:t?.provider}:{ready:!1});return Zt(()=>{if(!i)return;let d=!1;return import("./maps/google/index.js").then(({googleProvider:l})=>{d||a({ready:!0,provider:l({apiKey:i,mapId:r,mapOptions:s,styles:o})})}),()=>{d=!0}},[i,r]),n}function ei({onFiltersChange:t}){let e=Xt(t);return e.current=t,Ve("FiltersChanged",i=>{i.type==="FiltersChanged"&&e.current(i.filters)}),null}function Pn(t){let{datasets:e,filters:i,map:r,components:s,initialFilters:o,onFiltersChange:n,mobileAction:a,search:d,toolbarEnd:l,mapControls:c,config:h,autoFetch:b,className:w}=t,{ready:k,provider:p}=Yt(r);if(!k)return null;let F=[];for(let A of e)F.push(ke(A));i&&F.push(Ee(i)),p&&F.push(we(p)),o&&F.push(xe(o)),h&&F.push(Ie(h));let O=Se(...F),_={...Qe,...s};return ti(We,{...O,children:[n&&Fe(ei,{onFiltersChange:n}),Fe(Re,{..._,children:Fe(et,{className:w,search:d,toolbarEnd:l,mobileAction:a,autoFetch:b,mapCenter:r?.center,mapZoom:r?.zoom,mapControls:c})})]})}export{Q as a,H as b,G as c,Z as d,Ce as e,X as f,J as g,Se as h,Ie as i,we as j,ke as k,Ee as l,yi as m,xe as n,vi as o,le as p,Re as q,P as r,Y as s,g as t,I as u,ee as v,de as w,z as x,Oe as y,ze as z,Ke as A,Ue as B,Ve as C,We as D,ce as E,ue as F,me as G,ge as H,fe as I,ve as J,he as K,Le as L,be as M,Pe as N,Qe as O,Ge as P,Xe as Q,et as R,Pn as S};
|
package/dist/chunk-X4LBPNOS.cjs
DELETED
|
@@ -1,2 +0,0 @@
|
|
|
1
|
-
"use strict";Object.defineProperty(exports, "__esModule", {value: true}); function _interopRequireWildcard(obj) { if (obj && obj.__esModule) { return obj; } else { var newObj = {}; if (obj != null) { for (var key in obj) { if (Object.prototype.hasOwnProperty.call(obj, key)) { newObj[key] = obj[key]; } } } newObj.default = obj; return newObj; } } function _nullishCoalesce(lhs, rhsFn) { if (lhs != null) { return lhs; } else { return rhsFn(); } } function _optionalChain(ops) { let lastAccessLHS = undefined; let value = ops[0]; let i = 1; while (i < ops.length) { const op = ops[i]; const fn = ops[i + 1]; i += 2; if ((op === 'optionalAccess' || op === 'optionalCall') && value == null) { return undefined; } if (op === 'access' || op === 'optionalAccess') { lastAccessLHS = value; value = fn(value); } else if (op === 'call' || op === 'optionalCall') { value = fn((...args) => value.call(lastAccessLHS, ...args)); lastAccessLHS = undefined; } } return value; } var _class; var _class2; var _class3; var _class4; var _class5;"use client";
|
|
2
|
-
var Q= (_class =class{__init() {this.listeners=new Set}constructor(e){;_class.prototype.__init.call(this);this.state=this.freezeState({filters:{...e.filters},results:{items:[],nextCursor:null},bounds:null,selection:null,hovered:null,pagination:{mode:_nullishCoalesce(e.mode, () => ("paged")),loading:!1},layers:{},points:{}})}getState(){return this.state}setFilters(e){this.setState({filters:{...this.state.filters,...e}})}setResults(e){this.setState({results:{items:[...e.items],nextCursor:e.nextCursor,total:e.total}})}appendResults(e){this.setState({results:{items:[...this.state.results.items,...e.items],nextCursor:e.nextCursor,total:e.total}})}setBounds(e){this.setState({bounds:e?{...e}:null})}setSelection(e){this.setState({selection:e})}setHovered(e){this.setState({hovered:e})}setLayerVisible(e,i){this.setState({layers:{...this.state.layers,[e]:i}})}setLoading(e){this.setState({pagination:{...this.state.pagination,loading:e}})}setPoints(e,i){this.setState({points:{...this.state.points,[e]:[...i]}})}subscribe(e){return this.listeners.add(e),()=>{this.listeners.delete(e)}}setState(e){this.state=this.freezeState({...this.state,...e}),this.notify()}notify(){for(let e of this.listeners)e()}freezeState(e){Object.freeze(e.filters),Object.freeze(e.results.items),Object.freeze(e.results),e.bounds&&Object.freeze(e.bounds),Object.freeze(e.pagination),Object.freeze(e.layers);for(let i of Object.values(e.points))Object.freeze(i);return Object.freeze(e.points),Object.freeze(e)}}, _class);var H= (_class2 =class{constructor() { _class2.prototype.__init2.call(this); }__init2() {this.defs=new Map}add(e){if(this.defs.has(e.key))throw new Error(`FilterRegistry: filter "${e.key}" is already registered`);return this.defs.set(e.key,{...e}),this}remove(e){return this.defs.delete(e),this}replace(e,i){if(!this.defs.has(e))throw new Error(`FilterRegistry: cannot replace unregistered filter "${e}"`);return this.defs.set(e,{...i,key:e}),this}reorder(e){let i=this.list(),r=e.filter(o=>this.defs.has(o));r.forEach((o,n)=>{this.defs.get(o).order=n});let s=new Set(r);return i.filter(o=>!s.has(o.key)).forEach((o,n)=>{o.order=r.length+n}),this}list(){return[...this.defs.values()].sort((e,i)=>e.order-i.order)}has(e){return this.defs.has(e)}toFilters(e){return this.list().filter(r=>Object.hasOwn(e,r.key)).map(r=>r.toParams(e[r.key])).reduce((r,s)=>({...r,...s}),{})}activeKeys(e){return this.list().filter(i=>_optionalChain([i, 'access', _2 => _2.isActive, 'optionalCall', _3 => _3(e)])).map(i=>i.key)}clearedParams(){return this.list().reduce((e,i)=>Object.assign(e,i.toParams(i.fromParams({}))),{})}}, _class2);var G= (_class3 =class{constructor() { _class3.prototype.__init3.call(this); }__init3() {this.defs=new Map}add(e){if(this.defs.has(e.id))throw new Error(`DatasetRegistry: dataset "${e.id}" is already registered`);return this.defs.set(e.id,{...e}),this}get(e){return this.defs.get(e)}has(e){return this.defs.has(e)}list(){return[...this.defs.values()]}visibleIds(){return this.list().filter(e=>_optionalChain([e, 'access', _4 => _4.visible, 'optionalCall', _5 => _5()])!==!1).map(e=>e.id)}}, _class3);var Z= (_class4 =class{constructor() { _class4.prototype.__init4.call(this); }__init4() {this.map=new Map}dispose(){this.map.clear()}emit(e){let i=this.map.get(e.type);if(i)for(let s of[...i])s(e);let r=this.map.get("*");if(r)for(let s of[...r])s(e)}on(e,i){let r=this.map.get(e);return r||(r=new Set,this.map.set(e,r)),r.add(i),()=>{r.delete(i)}}}, _class4);var Ce={pagination:"paged",pageSize:20,debounceMs:250};var X=class{constructor(e){this.options=Object.freeze({...Ce,...e})}};var J= (_class5 =class{__init5() {this.emitter=new Z}__init6() {this.debounceTimer=null}__init7() {this.debounceResolve=null}__init8() {this.queryToken=0}__init9() {this.pointsToken=0}constructor(e){;_class5.prototype.__init5.call(this);_class5.prototype.__init6.call(this);_class5.prototype.__init7.call(this);_class5.prototype.__init8.call(this);_class5.prototype.__init9.call(this);this.datasets=e.datasets,this.filters=_nullishCoalesce(e.filters, () => (new H)),this.map=e.map,this.config=new X(e.config);let i=_nullishCoalesce(e.primaryDatasetId, () => (_optionalChain([this, 'access', _6 => _6.datasets, 'access', _7 => _7.list, 'call', _8 => _8(), 'access', _9 => _9[0], 'optionalAccess', _10 => _10.id])));if(i==null||!this.datasets.has(i))throw new Error(`ListingEngine: primary dataset "${_nullishCoalesce(i, () => (""))}" is not registered \u2014 pass a valid primaryDatasetId or register at least one dataset`);this.primaryDatasetId=i,this.store=new Q({filters:_nullishCoalesce(e.initialFilters, () => ({})),mode:this.config.options.pagination})}get state(){return this.store.getState()}get options(){return this.config.options}applyFilters(e){this.store.setFilters(e),this.emitter.emit({type:"FiltersChanged",filters:this.currentFilters()}),this.clearDebounce();let i=++this.queryToken,r=this.config.options.debounceMs;return r<=0?this.runQuery(i):new Promise(s=>{this.debounceResolve=s,this.debounceTimer=setTimeout(()=>{this.debounceTimer=null,this.debounceResolve=null,s(this.runQuery(i))},r)})}async loadPage(){let e=this.state.results.nextCursor;if(e===null)return;let i=++this.queryToken,r=this.primaryDataset();this.store.setLoading(!0);try{let s=await r.adapter.list(this.currentFilters(),{cursor:e,limit:this.config.options.pageSize});if(i!==this.queryToken)return;this.config.options.pagination==="infinite"?this.store.appendResults(s):this.store.setResults(s),this.emitter.emit({type:"ResultsLoaded",datasetId:this.primaryDatasetId,count:s.items.length})}finally{i===this.queryToken&&this.store.setLoading(!1)}}async loadPoints(e){this.store.setBounds(e),this.emitter.emit({type:"BoundsChanged",bounds:e});let i=this.currentFilters(),r=++this.pointsToken;await Promise.allSettled(this.datasets.visibleIds().map(async s=>{let o=this.datasets.get(s);if(!o)return;let n=await o.adapter.getPoints(i,e);r===this.pointsToken&&this.store.setPoints(s,n)}))}selectPoint(e,i){this.store.setSelection(i);let r=_optionalChain([this, 'access', _11 => _11.state, 'access', _12 => _12.points, 'access', _13 => _13[e], 'optionalAccess', _14 => _14.find, 'call', _15 => _15(s=>s.id===i)]);r&&this.emitter.emit({type:"PointClicked",datasetId:e,id:r.id,entity:r.entity})}setHovered(e,i){this.store.setHovered(i)}toggleLayer(e){let r=!(_nullishCoalesce(this.state.layers[e], () => (!0)));this.store.setLayerVisible(e,r),this.emitter.emit({type:"LayerToggled",datasetId:e,visible:r})}subscribe(e){return this.store.subscribe(e)}on(e,i){return this.emitter.on(e,i)}dispose(){this.clearDebounce(),this.emitter.dispose()}async runQuery(e){if(e!==this.queryToken)return;let i=this.primaryDataset();this.store.setLoading(!0);try{let r=await i.adapter.list(this.currentFilters(),{cursor:null,limit:this.config.options.pageSize});if(e!==this.queryToken)return;this.store.setResults(r),this.emitter.emit({type:"ResultsLoaded",datasetId:this.primaryDatasetId,count:r.items.length})}finally{e===this.queryToken&&this.store.setLoading(!1)}}primaryDataset(){return this.datasets.get(this.primaryDatasetId)}currentFilters(){return this.store.getState().filters}clearDebounce(){this.debounceTimer!==null&&(clearTimeout(this.debounceTimer),this.debounceTimer=null),this.debounceResolve!==null&&(this.debounceResolve(),this.debounceResolve=null)}}, _class5);function Se(...t){let e={config:{},filters:new H,datasets:new G};for(let i of t)i(e);return e}var Ie=t=>e=>{e.config={...e.config,...t}},we= exports.j =t=>e=>{e.map=t},ke= exports.k =t=>e=>{e.datasets.add(t)},Ee= exports.l =t=>e=>{t(e.filters)},yi= exports.m =t=>e=>{e.urlSync=t},xe= exports.n =t=>e=>{e.initialFilters=t},vi= exports.o =t=>e=>{e.primaryDatasetId=t};var _react = require('react');var _jsxruntime = require('react/jsx-runtime');function nt(t){return String(_nullishCoalesce(_optionalChain([t, 'optionalAccess', _16 => _16.title]), () => ("")))}var st=({item:t})=>_jsxruntime.jsx.call(void 0, "div",{children:nt(t)}),ot=()=>_jsxruntime.jsx.call(void 0, "div",{}),le= exports.p =()=>_jsxruntime.jsx.call(void 0, "div",{}),at=({children:t})=>_jsxruntime.jsx.call(void 0, "div",{children:t}),lt=({children:t})=>_jsxruntime.jsx.call(void 0, "div",{children:t}),dt=({value:t,onChange:e,placeholder:i})=>_jsxruntime.jsx.call(void 0, "input",{type:"search",value:t,placeholder:i,onChange:r=>e(r.target.value),"aria-label":_nullishCoalesce(i, () => ("Search"))}),pt=()=>_jsxruntime.jsx.call(void 0, "div",{role:"status",children:"No results"}),ct=()=>_jsxruntime.jsx.call(void 0, "div",{role:"status","aria-busy":"true",children:"Loading\u2026"}),ut=({count:t})=>_jsxruntime.jsxs.call(void 0, "div",{children:[t," results"]}),mt=({children:t})=>_jsxruntime.jsx.call(void 0, "div",{children:t}),C={Card:st,Marker:ot,Popup:le,Sidebar:at,FilterPanel:lt,Search:dt,Empty:pt,Loading:ct,ResultHeader:ut,Toolbar:mt},Ne=_react.createContext.call(void 0, C);function Re(t){let{Card:e,Marker:i,Popup:r,Sidebar:s,FilterPanel:o,Search:n,Empty:a,Loading:d,ResultHeader:l,Toolbar:c,children:h}=t,b={Card:_nullishCoalesce(e, () => (C.Card)),Marker:_nullishCoalesce(i, () => (C.Marker)),Popup:_nullishCoalesce(r, () => (C.Popup)),Sidebar:_nullishCoalesce(s, () => (C.Sidebar)),FilterPanel:_nullishCoalesce(o, () => (C.FilterPanel)),Search:_nullishCoalesce(n, () => (C.Search)),Empty:_nullishCoalesce(a, () => (C.Empty)),Loading:_nullishCoalesce(d, () => (C.Loading)),ResultHeader:_nullishCoalesce(l, () => (C.ResultHeader)),Toolbar:_nullishCoalesce(c, () => (C.Toolbar))};return _jsxruntime.jsx.call(void 0, Ne.Provider,{value:b,children:h})}function P(){return _react.useContext.call(void 0, Ne)}var Y=_react.createContext.call(void 0, null);function g(){let t=_react.useContext.call(void 0, Y);if(t===null)throw new Error("useListing must be used within a <ListingProvider>");return t}function I(){let t=g(),e=_react.useCallback.call(void 0, r=>t.subscribe(r),[t]),i=_react.useCallback.call(void 0, ()=>t.state,[t]);return _react.useSyncExternalStore.call(void 0, e,i,i)}function ee(){let t=g(),e=I(),i=_react.useCallback.call(void 0, s=>t.applyFilters(s),[t]),r=_react.useCallback.call(void 0, (s,o)=>t.applyFilters({[s]:o}),[t]);return{filters:e.filters,set:i,setField:r}}function de({className:t,groupClassName:e,hideLabels:i}={}){let r=g(),{FilterPanel:s}=P(),{filters:o}=ee();return _jsxruntime.jsx.call(void 0, s,{children:_jsxruntime.jsx.call(void 0, "div",{className:_nullishCoalesce(t, () => ("space-y-5")),children:r.filters.list().map(n=>{if(typeof n.render=="string")return _jsxruntime.jsx.call(void 0, "div",{"data-filter":n.key,className:e},n.key);let a=n.render;return _jsxruntime.jsxs.call(void 0, "div",{className:e,children:[n.label&&!i&&_jsxruntime.jsx.call(void 0, "div",{className:"mb-1.5 text-[13px] font-medium text-foreground",children:n.label}),_jsxruntime.jsx.call(void 0, a,{value:n.fromParams(o),onChange:d=>{r.applyFilters(n.toParams(d))}})]},n.key)})})})}function z(){return I().results}function Lt(t,e){if(t&&typeof t=="object"&&"id"in t){let i=t.id;if(typeof i=="string"||typeof i=="number")return i}return e}function Oe({className:t}={}){let e=g(),{items:i}=z(),{pagination:r,selection:s}=I(),{Card:o,Empty:n,Loading:a}=P();return r.loading&&i.length===0?_jsxruntime.jsx.call(void 0, a,{}):i.length===0?_jsxruntime.jsx.call(void 0, n,{}):_jsxruntime.jsx.call(void 0, "div",{role:"list",className:t,children:i.map((d,l)=>{let c=Lt(d,l);return _jsxruntime.jsx.call(void 0, o,{item:d,selected:s===c,onSelect:()=>e.selectPoint(e.primaryDatasetId,c)},c)})})}var _reactdom = require('react-dom');var Pt={west:-179.9,south:-85,east:179.9,north:85},Be=.1,Ae=.02;function Tt(t){if(t.length===0)return null;let e=t[0].lng,i=t[0].lng,r=t[0].lat,s=t[0].lat;for(let{lat:a,lng:d}of t)d<e&&(e=d),d>i&&(i=d),a<r&&(r=a),a>s&&(s=a);let o=s>r?(s-r)*Be:Ae,n=i>e?(i-e)*Be:Ae;return{west:e-n,east:i+n,south:r-o,north:s+o}}function ze(t){let{center:e,zoom:i,fallback:r,mapControls:s}=t,o=g(),n=I(),a=_react.useRef.call(void 0, null),d=_react.useRef.call(void 0, null),l=_react.useRef.call(void 0, null),[c,h]=_react.useState.call(void 0, !1),b=_react.useRef.call(void 0, !1),w=_react.useRef.call(void 0, !1),k=_react.useRef.call(void 0, !1),p=o.map;_react.useEffect.call(void 0, ()=>{let L=l.current;if(!p||!L)return;let f=[];for(let u of Object.keys(n.points)){if(n.layers[u]===!1)continue;let y=o.datasets.get(u),R=_nullishCoalesce(n.points[u], () => ([])),ae={id:u,markers:R.map(M=>({id:M.id,position:M.position,iconUrl:_optionalChain([y, 'optionalAccess', _17 => _17.marker, 'access', _18 => _18.iconUrl, 'optionalCall', _19 => _19(M.entity)]),element:_optionalChain([y, 'optionalAccess', _20 => _20.marker, 'access', _21 => _21.element, 'optionalCall', _22 => _22(M.entity)])})),clustering:_optionalChain([y, 'optionalAccess', _23 => _23.clustering]),onMarkerClick:M=>o.selectPoint(u,M)};f.push(p.renderLayer(L,ae))}return()=>{f.forEach(u=>u())}},[o,p,c,n.points,n.layers]),_react.useEffect.call(void 0, ()=>{if(!a.current||!p)return;let L=a.current,f=!1,u=null;return(async()=>{let y=await p.mount(L,{center:e,zoom:i,fullscreenTarget:_nullishCoalesce(d.current, () => (void 0))});if(f){p.destroy(y);return}l.current=y,u=p.onBoundsChange(y,R=>{k.current?k.current=!1:w.current=!0,o.loadPoints(R)}),h(!0),o.loadPoints(Pt)})(),()=>{f=!0,_optionalChain([u, 'optionalCall', _24 => _24()]),l.current&&(p.destroy(l.current),l.current=null),h(!1)}},[o,p]),_react.useEffect.call(void 0, ()=>{let L=l.current;if(!p||!L||e||b.current||w.current)return;let f=[];for(let y of Object.keys(n.points))if(n.layers[y]!==!1)for(let R of _nullishCoalesce(n.points[y], () => ([])))f.push(R.position);let u=Tt(f);u&&(b.current=!0,k.current=!0,p.fitBounds(L,u))},[p,e,c,n.points,n.layers]),_react.useEffect.call(void 0, ()=>{_optionalChain([p, 'optionalAccess', _25 => _25.updateMarkerStates, 'call', _26 => _26(n.selection,n.hovered)])},[p,c,n.selection,n.hovered]);let{Popup:F}=P(),O=F!==le,_=_nullishCoalesce(n.points[o.primaryDatasetId], () => ([])),A=n.selection!=null?_.find(L=>L.id===n.selection):void 0,[V,j]=_react.useState.call(void 0, null),N=_react.useRef.call(void 0, A);return N.current=A,_react.useEffect.call(void 0, ()=>{let L=l.current;if(!p||!L||!O)return;let f=N.current;if(!f)return;let u=p.mountOverlay(f.position);j({entity:f.entity,position:f.position,container:u.container});let y=()=>o.selectPoint(o.primaryDatasetId,null),R=M=>{M.key==="Escape"&&y()};document.addEventListener("keydown",R);let ae=p.onMapClick(y);return()=>{document.removeEventListener("keydown",R),ae(),u.unmount(),j(null)}},[o,p,c,n.selection,O]),_jsxruntime.jsxs.call(void 0, "div",{ref:d,className:"relative h-full min-h-0 w-full",children:[_jsxruntime.jsxs.call(void 0, "div",{ref:a,className:!p&&r?"flex h-full min-h-0 w-full items-center justify-center":"h-full min-h-0 w-full",children:[!p&&r,O&&V?_reactdom.createPortal.call(void 0, _jsxruntime.jsx.call(void 0, F,{entity:V.entity,onClose:()=>o.selectPoint(o.primaryDatasetId,null)}),V.container):null]}),s!=null&&_jsxruntime.jsx.call(void 0, "div",{className:"pointer-events-none absolute inset-0",children:_jsxruntime.jsx.call(void 0, "div",{className:"pointer-events-auto",children:s})})]})}function Ke(){let t=g(),{results:e,pagination:i}=I();return e.nextCursor==null?null:_jsxruntime.jsx.call(void 0, "button",{type:"button",disabled:i.loading,onClick:()=>{t.loadPage()},children:"Load more"})}function Ue(){let{items:t,total:e}=z(),{ResultHeader:i}=P();return _jsxruntime.jsx.call(void 0, i,{count:t.length,total:e})}function Ve(t,e){let i=g(),r=_react.useRef.call(void 0, e);r.current=e,_react.useEffect.call(void 0, ()=>i.on(t,s=>r.current(s)),[i,t])}function We(t){let{children:e,...i}=t,[r]=_react.useState.call(void 0, ()=>i),[s,o]=_react.useState.call(void 0, null);return _react.useEffect.call(void 0, ()=>{let n=new J({datasets:r.datasets,filters:r.filters,config:r.config,map:r.map,initialFilters:r.initialFilters,primaryDatasetId:r.primaryDatasetId});return r.urlSync&&r.urlSync.start(n),o(n),()=>{r.urlSync&&r.urlSync.stop(),n.dispose(),o(a=>a===n?null:a)}},[r]),s?_jsxruntime.jsx.call(void 0, Y.Provider,{value:s,children:e}):null}function K(t){return typeof t!="number"?t:new Intl.NumberFormat("en-US",{style:"currency",currency:"USD",maximumFractionDigits:0}).format(t)}function Et(t){return t?"rle-card rle-card--selected":"rle-card"}function ce({item:t,selected:e,onSelect:i}){let r=_nullishCoalesce(t, () => ({})),s=Et(e),o=_jsxruntime.jsxs.call(void 0, _jsxruntime.Fragment,{children:[r.imageUrl?_jsxruntime.jsx.call(void 0, "img",{src:r.imageUrl,alt:_nullishCoalesce(r.title, () => ("")),className:"rle-card-media"}):_jsxruntime.jsx.call(void 0, "div",{className:"rle-card-media rle-card-media--placeholder","aria-hidden":"true"}),_jsxruntime.jsxs.call(void 0, "div",{className:"rle-card-body",children:[r.title&&_jsxruntime.jsx.call(void 0, "span",{className:"rle-card-title",children:r.title}),r.subtitle&&_jsxruntime.jsx.call(void 0, "span",{className:"rle-card-address",children:r.subtitle}),r.badge&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-card-info",children:_jsxruntime.jsx.call(void 0, "span",{className:"rle-card-info-item",children:r.badge})}),r.price!=null&&_jsxruntime.jsx.call(void 0, "span",{className:"rle-card-price",children:K(r.price)})]})]});return i?_jsxruntime.jsx.call(void 0, "button",{type:"button",onClick:i,"aria-pressed":_nullishCoalesce(e, () => (!1)),className:s,children:o}):_jsxruntime.jsx.call(void 0, "article",{className:s,children:o})}function ue(t){return _jsxruntime.jsxs.call(void 0, "div",{role:"status",className:"rle-empty",children:[_jsxruntime.jsxs.call(void 0, "svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:1.5,strokeLinecap:"round",strokeLinejoin:"round",className:"rle-empty-icon","aria-hidden":"true",children:[_jsxruntime.jsx.call(void 0, "circle",{cx:"11",cy:"11",r:"7"}),_jsxruntime.jsx.call(void 0, "path",{d:"m21 21-4.3-4.3"})]}),_jsxruntime.jsx.call(void 0, "p",{className:"rle-empty-title",children:"No results"}),_jsxruntime.jsx.call(void 0, "p",{className:"rle-empty-hint",children:"Try adjusting your filters or search terms."})]})}function me({children:t}){return _jsxruntime.jsx.call(void 0, "div",{className:"rle-filter-panel",children:t})}function ge(t){return _jsxruntime.jsx.call(void 0, "div",{className:"rle-loading",role:"status","aria-busy":"true","aria-label":"Loading results",children:Array.from({length:3}).map((e,i)=>_jsxruntime.jsxs.call(void 0, "div",{className:"rle-loading-item",children:[_jsxruntime.jsx.call(void 0, "div",{className:"rle-skeleton",style:{aspectRatio:"4 / 3",width:"100%"}}),_jsxruntime.jsx.call(void 0, "div",{className:"rle-skeleton",style:{height:16,width:"65%"}}),_jsxruntime.jsx.call(void 0, "div",{className:"rle-skeleton",style:{height:12,width:"35%"}})]},i))})}function fe({point:t}){let e=_nullishCoalesce(t.entity, () => ({}));return _jsxruntime.jsx.call(void 0, "span",{className:"rle-pin",children:e.price!=null?K(e.price):""})}function ve({entity:t,onClose:e}){let i=_nullishCoalesce(t, () => ({}));return _jsxruntime.jsxs.call(void 0, "div",{className:"rle-popup",role:"group","aria-label":"Location details",children:[_jsxruntime.jsx.call(void 0, "button",{type:"button",onClick:e,"aria-label":"Close",className:"rle-popup-close",children:_jsxruntime.jsxs.call(void 0, "svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round",width:"16",height:"16","aria-hidden":"true",children:[_jsxruntime.jsx.call(void 0, "path",{d:"M18 6 6 18"}),_jsxruntime.jsx.call(void 0, "path",{d:"m6 6 12 12"})]})}),_jsxruntime.jsxs.call(void 0, "div",{children:[i.title&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-card-title",children:i.title}),i.subtitle&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-card-address",children:i.subtitle}),i.price!=null&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-card-price",children:K(i.price)})]})]})}function he({count:t,total:e}){let i=e!=null&&e!==t?`${t} of ${e} results`:`${t} results`;return _jsxruntime.jsx.call(void 0, "div",{className:"rle-result-header",children:i})}function Le({value:t,onChange:e,placeholder:i}){return _jsxruntime.jsx.call(void 0, "input",{type:"search",value:t,placeholder:i,onChange:r=>e(r.target.value),"aria-label":_nullishCoalesce(i, () => ("Search")),className:"rle-input"})}function be({children:t}){return _jsxruntime.jsx.call(void 0, "aside",{className:"rle-sidebar",children:t})}function Pe({children:t}){return _jsxruntime.jsx.call(void 0, "div",{className:"rle-toolbar",children:t})}var Qe={Card:ce,Marker:fe,Popup:ve,Sidebar:be,FilterPanel:me,Search:Le,Empty:ue,Loading:ge,ResultHeader:he,Toolbar:Pe};function Ge({view:t,onViewChange:e}){return _jsxruntime.jsx.call(void 0, "nav",{className:"rle-bottom-nav","aria-label":"Listing navigation",children:_jsxruntime.jsxs.call(void 0, "div",{className:"rle-viewtoggle",role:"group","aria-label":"View",children:[_jsxruntime.jsxs.call(void 0, "button",{type:"button",className:`rle-viewtoggle__btn${t==="list"?" rle-viewtoggle__btn--active":""}`,"aria-pressed":t==="list",onClick:()=>e("list"),children:[_jsxruntime.jsx.call(void 0, At,{}),"List"]}),_jsxruntime.jsxs.call(void 0, "button",{type:"button",className:`rle-viewtoggle__btn${t==="map"?" rle-viewtoggle__btn--active":""}`,"aria-pressed":t==="map",onClick:()=>e("map"),children:[_jsxruntime.jsx.call(void 0, Ht,{}),"Map"]})]})})}function At(){return _jsxruntime.jsxs.call(void 0, "svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round",width:"16",height:"16","aria-hidden":"true",children:[_jsxruntime.jsx.call(void 0, "line",{x1:"8",y1:"6",x2:"20",y2:"6"}),_jsxruntime.jsx.call(void 0, "line",{x1:"8",y1:"12",x2:"20",y2:"12"}),_jsxruntime.jsx.call(void 0, "line",{x1:"8",y1:"18",x2:"20",y2:"18"}),_jsxruntime.jsx.call(void 0, "line",{x1:"4",y1:"6",x2:"4.01",y2:"6"}),_jsxruntime.jsx.call(void 0, "line",{x1:"4",y1:"12",x2:"4.01",y2:"12"}),_jsxruntime.jsx.call(void 0, "line",{x1:"4",y1:"18",x2:"4.01",y2:"18"})]})}function Ht(){return _jsxruntime.jsxs.call(void 0, "svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round",width:"16",height:"16","aria-hidden":"true",children:[_jsxruntime.jsx.call(void 0, "polygon",{points:"1 6 8 3 16 6 23 3 23 18 16 21 8 18 1 21 1 6"}),_jsxruntime.jsx.call(void 0, "line",{x1:"8",y1:"3",x2:"8",y2:"18"}),_jsxruntime.jsx.call(void 0, "line",{x1:"16",y1:"6",x2:"16",y2:"21"})]})}function Xe({open:t,onOpenChange:e,title:i,children:r,footer:s}){let o=_react.useRef.call(void 0, null),[n,a]=_react.useState.call(void 0, !1),[d,l]=_react.useState.call(void 0, !1);return _react.useEffect.call(void 0, ()=>{if(!t){l(!1),a(!1);return}a(!0);let c=requestAnimationFrame(()=>l(!0));return()=>cancelAnimationFrame(c)},[t]),_react.useEffect.call(void 0, ()=>{if(!n)return;let c=document.body.style.overflow;return document.body.style.overflow="hidden",()=>{document.body.style.overflow=c}},[n]),_react.useEffect.call(void 0, ()=>{if(!n)return;_optionalChain([o, 'access', _27 => _27.current, 'optionalAccess', _28 => _28.focus, 'call', _29 => _29()]);function c(h){h.key==="Escape"&&e(!1)}return document.addEventListener("keydown",c),()=>document.removeEventListener("keydown",c)},[n,e]),!n||typeof document>"u"?null:_reactdom.createPortal.call(void 0, _jsxruntime.jsxs.call(void 0, _jsxruntime.Fragment,{children:[_jsxruntime.jsx.call(void 0, "div",{className:`rle-sheet-backdrop${d?" rle-sheet-backdrop--open":""}`,onClick:()=>e(!1),"aria-hidden":"true"}),_jsxruntime.jsxs.call(void 0, "div",{ref:o,className:`rle-sheet${d?" rle-sheet--open":""}`,role:"dialog","aria-modal":"true","aria-label":i,tabIndex:-1,children:[_jsxruntime.jsx.call(void 0, "div",{className:"rle-sheet__handle","aria-hidden":"true"}),_jsxruntime.jsxs.call(void 0, "div",{className:"rle-sheet__header",children:[i&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-sheet__title",children:i}),_jsxruntime.jsx.call(void 0, "button",{type:"button",className:"rle-sheet__close",onClick:()=>e(!1),"aria-label":"Close",children:_jsxruntime.jsx.call(void 0, Ut,{})})]}),_jsxruntime.jsx.call(void 0, "div",{className:"rle-sheet__body",children:r}),s&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-sheet__footer",children:s})]})]}),document.body)}function Ut(){return _jsxruntime.jsxs.call(void 0, "svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round",width:"16",height:"16","aria-hidden":"true",children:[_jsxruntime.jsx.call(void 0, "path",{d:"M18 6 6 18"}),_jsxruntime.jsx.call(void 0, "path",{d:"m6 6 12 12"})]})}function Je({search:t,onFiltersClick:e,filterCount:i=0,action:r}){let{Search:s}=P();return _jsxruntime.jsxs.call(void 0, "header",{className:"rle-mobile-header",children:[t&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-mobile-header__search",children:_jsxruntime.jsx.call(void 0, s,{value:t.value,onChange:t.onChange,placeholder:t.placeholder})}),_jsxruntime.jsxs.call(void 0, "button",{type:"button",className:"rle-btn rle-mobile-header__btn",onClick:e,children:[_jsxruntime.jsx.call(void 0, $t,{}),_jsxruntime.jsx.call(void 0, "span",{children:"Filters"}),i>0&&_jsxruntime.jsx.call(void 0, "span",{className:"rle-mobile-header__count",children:i})]}),r&&_jsxruntime.jsx.call(void 0, "button",{type:"button",className:"rle-btn rle-mobile-header__btn rle-mobile-header__btn--icon",onClick:r.onClick,"aria-label":r.label,children:_nullishCoalesce(r.icon, () => (_jsxruntime.jsx.call(void 0, Wt,{})))})]})}function $t(){return _jsxruntime.jsxs.call(void 0, "svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round","aria-hidden":"true",children:[_jsxruntime.jsx.call(void 0, "line",{x1:"4",y1:"6",x2:"20",y2:"6"}),_jsxruntime.jsx.call(void 0, "circle",{cx:"9",cy:"6",r:"2",fill:"currentColor",stroke:"none"}),_jsxruntime.jsx.call(void 0, "line",{x1:"4",y1:"12",x2:"20",y2:"12"}),_jsxruntime.jsx.call(void 0, "circle",{cx:"15",cy:"12",r:"2",fill:"currentColor",stroke:"none"}),_jsxruntime.jsx.call(void 0, "line",{x1:"4",y1:"18",x2:"20",y2:"18"}),_jsxruntime.jsx.call(void 0, "circle",{cx:"11",cy:"18",r:"2",fill:"currentColor",stroke:"none"})]})}function Wt(){return _jsxruntime.jsxs.call(void 0, "svg",{xmlns:"http://www.w3.org/2000/svg",viewBox:"0 0 24 24",fill:"none",stroke:"currentColor",strokeWidth:2,strokeLinecap:"round",strokeLinejoin:"round","aria-hidden":"true",children:[_jsxruntime.jsx.call(void 0, "line",{x1:"12",y1:"5",x2:"12",y2:"19"}),_jsxruntime.jsx.call(void 0, "line",{x1:"5",y1:"12",x2:"19",y2:"12"})]})}var jt=_jsxruntime.jsx.call(void 0, "div",{className:"rle-empty",children:"Map unavailable"});function Qt(){let t=_react.useRef.call(void 0, null),[e,i]=_react.useState.call(void 0, !0),[r,s]=_react.useState.call(void 0, !0);return _react.useEffect.call(void 0, ()=>{let o=t.current;if(!o)return;let n=()=>{let{clientWidth:h,scrollLeft:b,scrollWidth:w}=o;i(b<=0),s(b+h>=w-1)},a=0,d=()=>{a||(a=requestAnimationFrame(()=>{a=0,n()}))};n(),o.addEventListener("scroll",n,{passive:!0});let l,c;return typeof ResizeObserver<"u"&&(l=new ResizeObserver(n),l.observe(o)),typeof MutationObserver<"u"&&(c=new MutationObserver(d),c.observe(o,{characterData:!0,childList:!0,subtree:!0})),()=>{o.removeEventListener("scroll",n),_optionalChain([l, 'optionalAccess', _30 => _30.disconnect, 'call', _31 => _31()]),_optionalChain([c, 'optionalAccess', _32 => _32.disconnect, 'call', _33 => _33()]),a&&cancelAnimationFrame(a)}},[]),{atEnd:r,atStart:e,ref:t}}function et({search:t,toolbarEnd:e,mobileAction:i,autoFetch:r=!0,hasMap:s,mapCenter:o,mapZoom:n,mapControls:a,className:d}){let l=g(),{Search:c}=P(),h=z(),{filters:b,set:w}=ee(),k=_nullishCoalesce(s, () => (l.map!=null)),[p,F]=_react.useState.call(void 0, "list"),[O,_]=_react.useState.call(void 0, !1),{atEnd:A,atStart:V,ref:j}=Qt(),N=t?{value:String(_nullishCoalesce(b[t.filterKey], () => (""))),onChange:y=>{w({[t.filterKey]:y||void 0})},placeholder:t.placeholder}:void 0;_react.useEffect.call(void 0, ()=>{r!==!1&&l.applyFilters({})},[l,r]);let L=()=>{w(l.filters.clearedParams())},f=l.filters.activeKeys(b).length,u=_nullishCoalesce(h.total, () => (h.items.length));return _jsxruntime.jsxs.call(void 0, "div",{className:d?`rle-app ${d}`:"rle-app",children:[_jsxruntime.jsxs.call(void 0, "div",{className:"rle-filter-bar",children:[_jsxruntime.jsxs.call(void 0, "div",{className:"rle-filter-bar__scroll",ref:j,children:[N&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-filter-bar__search",children:_jsxruntime.jsx.call(void 0, c,{value:N.value,onChange:N.onChange,placeholder:N.placeholder})}),_jsxruntime.jsx.call(void 0, de,{className:"rle-filters-row",groupClassName:"rle-filter-group",hideLabels:!0})]}),!V&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-filter-bar__fade rle-filter-bar__fade--start","aria-hidden":"true"}),!A&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-filter-bar__fade rle-filter-bar__fade--end","aria-hidden":"true"})]}),_jsxruntime.jsx.call(void 0, Je,{search:N,onFiltersClick:()=>_(!0),filterCount:f,action:i}),_jsxruntime.jsxs.call(void 0, "div",{className:`rle-body ${k?"rle-split":"rle-body--list-only"}`,"data-mobile-view":p,children:[_jsxruntime.jsxs.call(void 0, "div",{className:"rle-list",children:[_jsxruntime.jsxs.call(void 0, "div",{className:"rle-list-header",children:[_jsxruntime.jsx.call(void 0, Ue,{}),e&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-list-header__toolbar",children:e})]}),_jsxruntime.jsx.call(void 0, Oe,{className:"rle-list-grid"}),_jsxruntime.jsx.call(void 0, Ke,{})]}),k&&_jsxruntime.jsx.call(void 0, "div",{className:"rle-map",children:_jsxruntime.jsx.call(void 0, ze,{center:o,zoom:n,fallback:jt,mapControls:a})})]}),k&&_jsxruntime.jsx.call(void 0, Ge,{view:p,onViewChange:F}),_jsxruntime.jsx.call(void 0, Xe,{title:"Filters",open:O,onOpenChange:_,footer:_jsxruntime.jsxs.call(void 0, _jsxruntime.Fragment,{children:[_jsxruntime.jsx.call(void 0, "button",{type:"button",className:"rle-btn rle-btn--ghost",onClick:L,children:"Clear all"}),_jsxruntime.jsxs.call(void 0, "button",{type:"button",className:"rle-btn rle-btn--primary",onClick:()=>_(!1),children:["Show ",u," results"]})]}),children:_jsxruntime.jsx.call(void 0, de,{className:"rle-filter-stack",groupClassName:"rle-filter-group"})})]})}function tt(t){return"provider"in t}function Yt(t){let e=t!=null&&!tt(t),i=e?t.apiKey:void 0,r=e?t.mapId:void 0,s=e?t.mapOptions:void 0,o=e?t.styles:void 0,[n,a]=_react.useState.call(void 0, ()=>!t||tt(t)?{ready:!0,provider:_optionalChain([t, 'optionalAccess', _34 => _34.provider])}:{ready:!1});return _react.useEffect.call(void 0, ()=>{if(!i)return;let d=!1;return Promise.resolve().then(() => _interopRequireWildcard(require("./maps/google/index.cjs"))).then(({googleProvider:l})=>{d||a({ready:!0,provider:l({apiKey:i,mapId:r,mapOptions:s,styles:o})})}),()=>{d=!0}},[i,r]),n}function ei({onFiltersChange:t}){let e=_react.useRef.call(void 0, t);return e.current=t,Ve("FiltersChanged",i=>{i.type==="FiltersChanged"&&e.current(i.filters)}),null}function Pn(t){let{datasets:e,filters:i,map:r,components:s,initialFilters:o,onFiltersChange:n,mobileAction:a,search:d,toolbarEnd:l,mapControls:c,config:h,autoFetch:b,className:w}=t,{ready:k,provider:p}=Yt(r);if(!k)return null;let F=[];for(let A of e)F.push(ke(A));i&&F.push(Ee(i)),p&&F.push(we(p)),o&&F.push(xe(o)),h&&F.push(Ie(h));let O=Se(...F),_={...Qe,...s};return _jsxruntime.jsxs.call(void 0, We,{...O,children:[n&&_jsxruntime.jsx.call(void 0, ei,{onFiltersChange:n}),_jsxruntime.jsx.call(void 0, Re,{..._,children:_jsxruntime.jsx.call(void 0, et,{className:w,search:d,toolbarEnd:l,mobileAction:a,autoFetch:b,mapCenter:_optionalChain([r, 'optionalAccess', _35 => _35.center]),mapZoom:_optionalChain([r, 'optionalAccess', _36 => _36.zoom]),mapControls:c})})]})}exports.a = Q; exports.b = H; exports.c = G; exports.d = Z; exports.e = Ce; exports.f = X; exports.g = J; exports.h = Se; exports.i = Ie; exports.j = we; exports.k = ke; exports.l = Ee; exports.m = yi; exports.n = xe; exports.o = vi; exports.p = le; exports.q = Re; exports.r = P; exports.s = Y; exports.t = g; exports.u = I; exports.v = ee; exports.w = de; exports.x = z; exports.y = Oe; exports.z = ze; exports.A = Ke; exports.B = Ue; exports.C = Ve; exports.D = We; exports.E = ce; exports.F = ue; exports.G = me; exports.H = ge; exports.I = fe; exports.J = ve; exports.K = he; exports.L = Le; exports.M = be; exports.N = Pe; exports.O = Qe; exports.P = Ge; exports.Q = Xe; exports.R = et; exports.S = Pn;
|